home *** CD-ROM | disk | FTP | other *** search
/ Visual Basic Source Code / Visual Basic Source Code.iso / vbsource / optivc32 / handbook.txt < prev    next >
Text File  |  1999-03-06  |  110KB  |  2,219 lines

  1.        OOOOOO                            VV        VV
  2.       OO    OO   PPPPPPP   TTTTTTTT  II   VV      VV  EEEEEE   CCCCCC
  3.       OO    OO   PP    PP     TT     II    VV    VV   EE       CC
  4.       OO    OO   PPPPPPP      TT     II     VV   VV   EEEEEE   CC
  5.       OO    OO   PP           TT     II       VVV     EE       CC
  6.        OOOOOO    PP           TT     II        V      EEEEEE   CCCCCC
  7.  
  8.  
  9.                        OptiVec  Version 1.5
  10.  
  11.  
  12.                       Dr. Martin Sander Software Development
  13.                       Serturnerstr. 11
  14.                       D-37085 Goettingen
  15.                       Germany
  16.                       e-mail: MartinSander@Bigfoot.com
  17.                       http://www.optivec.com
  18.  
  19.  
  20. For the full version, please order by e-mail or through our web-site!
  21. See chapter 1.3 for details.
  22.  
  23.  
  24. *****************************************************************************
  25.  
  26. F i r s t  P a r t :   File  HANDBOOK.TXT
  27.  
  28. !!     This is an ASCII text file!  It is best viewed with a simple        !!
  29. !!     DOS editor.                                                         !!
  30. !!     If you load this file into a word processor under Windows, you      !!
  31. !!     must use the filter "DOS text".                                     !!
  32. !!     Alternatively, you may use FCONVERT (shipped with Borland C++) to   !!
  33. !!     convert from ASCII (OEM) into the ANSI character set.               !!
  34. !!     preferably use the lettertype CourierNew 10 pt.                     !!
  35.  
  36. OptiCode (TM) and OptiVec (TM) are trademarks of Dr. Martin Sander
  37. Software Dev.  Other brand and product names mentioned in this handbook
  38. for identification purposes are trademarks or registered trademarks of
  39. their respective holders.
  40.  
  41.                  **************************************
  42.    German-speaking users:
  43.        Um die Kosten für das Herunterladen der Shareware-Version
  44.        über das Internet für alle so gering wie möglich zu halten,
  45.        enthält diese nur die englische Dokumentation. Sie finden
  46.        die deutsche Beschreibung separat unter
  47.              http://www.gwdg.de/~msander/Download/BC/OVDOCD.ZIP
  48.                  **************************************
  49.  
  50.  
  51. ****************************************************************************
  52. *                                                                          *
  53. *******                           Contents                           *******
  54. *                                                                          *
  55. ****************************************************************************
  56.  
  57. F i r s t  P a r t :   File  HANDBOOK.TXT
  58.  
  59. This HANDBOOK describes the main part of the OptiVec package, which
  60. is VectorLib. The other parts, CMATH and MatrixLib, have their own
  61. descriptions in separate files.
  62. MatrixLib: see Matrix.TXT
  63. CMATH:     see CMATH.TXT.
  64.  
  65. 1. Introduction
  66.     1.1 What is VectorLib and Why are the VectorLib Functions so Fast?
  67.     1.2 Licence Terms
  68.     1.3 Registered Versions
  69.     1.4 Getting Started
  70.  
  71. 2. The Elements of VectorLib Routines
  72.     2.1 The Data Types ui,  quad,  and extended
  73.     2.2 Complex Numbers: The Data Types fComplex,  dComplex,  eComplex
  74.     2.3 Vectors and Arrays: The Data Types fVector, dVector, eVector,
  75.         cfVector,  cdVector,  ceVector,   siVector, iVector, liVector,
  76.         usVector,  uVector,  ulVector,  qiVector,  and  uiVector
  77.     2.4 Real-number Functions: The Prefixes VF_,  VD_,  and VE_
  78.     2.5 Complex-number Functions: The Prefixes VCF_, VCD_, and VCE_
  79.     2.6 Functions of the Integer Data Types: The Prefixes VI_, VSI_,
  80.         VLI_, VQI_, VU_, VUS_, VUL_, and VUI_
  81.     2.7 Common Functions of Several Data Types: The Prefix V_
  82.  
  83. 3. The Environment
  84.     3.1 The Different Library Versions: Selecting Language, Memory Model,
  85.         and Processor
  86.  
  87. 4. VectorLib Functions and Routines: A Short Overview
  88.     4.1 Generation, Initialization and De-Allocation of Vectors
  89.     4.2 Index-oriented Manipulations
  90.     4.3 Data-Type Interconversions
  91.     4.4 More about Integer Arithmetics
  92.     4.5 Basic Functions of Complex Vectors
  93.     4.6 Mathematical Functions
  94.         4.6.1 Rounding
  95.         4.6.2 Comparisons
  96.         4.6.3 Direct Bit-Manipulation
  97.         4.6.4 Basic Arithmetics, Accumulations
  98.         4.6.5 Powers
  99.         4.6.6 Exponentials and Hyperbolic Functions
  100.         4.6.7 Logarithms
  101.         4.6.8 Trigonometric Functions
  102.     4.7 Analysis
  103.     4.8 Signal Processing:Fourier Transforms and Related Topics
  104.     4.9 Statistical Functions and Building Blocks
  105.     4.10 Input and Output
  106.     4.11 Graphics
  107.  
  108. 5. Error Handling
  109.     5.1 General Remarks
  110.     5.2 Integer Errors
  111.     5.3 Floating-Point Errors
  112.         5.3.1 Differences between Borland C++ 4.0 and earlier versions
  113.     5.4 The Treatment of Denormal Numbers
  114.     5.5 Advanced Error Handling: Writing Messages into a File
  115.  
  116. 6. Trouble-Shooting
  117.     6.1 General Problems
  118.     6.2 Problems with Windows 3.x?
  119.     6.3 Problems with Borland's 16-bit Linker?
  120.  
  121. 7. The include-files of VectorLib
  122.  
  123.  
  124. S e c o n d  P a r t :  File  FUNCREF.TXT
  125.  
  126.  8.  Alphabetical Reference
  127.  
  128.  9.  Non-vectorized Functions
  129.  
  130. 10. VectorLib Error Messages
  131.  
  132.  
  133.  
  134. ****************************************************************************
  135. *                                                                          *
  136. *******                       1. Introduction                        *******
  137. *                                                                          *
  138. ****************************************************************************
  139.  
  140.  
  141. 1.1 What is VectorLib and Why are the VectorLib Functions so Fast?
  142. ------------------------------------------------------------------
  143.  
  144. VectorLib offers a powerful library of routines for numerically demanding
  145. applications, making the philosophy of vectorized programming available for
  146. C/C++, Pascal, and Fortran languages. VectorLib serves to overcome the
  147. limitations of loop management of conventional compilers - which proved to
  148. be one of the largest obstacles in the programmer's way towards efficient
  149. coding for scientific and data analysis applications.
  150.  
  151. Conventionally, a vector, i.e. a one-dimensional array of data of the same
  152. type, would be processed by "dissolving" it into a loop over its elements,
  153. leaving it to the compiler to produce efficient code. Compiled code, however,
  154. is always far from perfect. This means that your computer is occupied with
  155. slow and often inaccurate calculations. Now, with VectorLib, things become
  156. easier: vectors are processed as a whole; they need no longer be dissolved
  157. into loops. A large set of strictly typed functions is defined and realized
  158. in a tight Assembler-written implementation.
  159.  
  160. In comparison to the old vector language APL, VectorLib has the advantage of
  161. being incorporated into the modern and versatile languages C/C++, Pascal, and
  162. Fortran. Recent versions of C++ and Fortran do already offer some sort of
  163. vector processing, by virtue of iterator classes using templates (C++) and
  164. field functions (Fortran90). Both of these, however, are basically a con-
  165. venient means of letting the compiler write the loop for you and then compile
  166. it to the usual inefficient code. The same is true for most implementations
  167. of the popular BLAS (Basic Linear Algebra Subroutine) libraries for Fortran.
  168. In comparison to these approaches, VectorLib is superior mainly with respect
  169. to execution speed - on the average by a factor of 2-3, in some cases even
  170. up to 8. The performance is no longer limited by the quality of your compiler,
  171. but rather by the real speed of the processor!
  172.  
  173. Moreover, the input and output vectors of VectorLib routines may be of
  174. variable size and it is possible to process only a part (e.g., the first 100
  175. elements, or every 10th element) of a vector, which is another important
  176. advantage of the VectorLib functions over other approaches, where only whole
  177. arrays are processed.
  178.  
  179. Using VectorLib routines instead of loops can make your source code much more
  180. compact and far better readable.
  181.  
  182. Besides this increased efficiency and ease of programming, the wide range of
  183. routines and functions covered by VectorLib makes this package the preferrable
  184. programming tool for scientific and data analysis applications, competing with
  185. many high-priced integrated systems, but imbedded into your favourite
  186. programming language:
  187.  
  188. *   All operators and mathematical functions of C/C++ are implemented in
  189.     vectorized form; additionally many more mathematical functions are
  190.     included which normally would have to be calculated by more or less
  191.     complicated combinations of existing functions. Not only the execution
  192.     speed, but also the accuracy of the results is greatly improved.
  193.  
  194. *   Building blocks for statistical data analysis are supplied.
  195.  
  196. *   Derivatives, integrals, interpolation schemes are included.
  197.  
  198. *   Fast Fourier Transform techniques allow for efficient convolutions,
  199.     correlation analyses, spectral filtering, and so on.
  200.  
  201. *   Graphical representation of data offers a convenient way of monitoring
  202.     the results of vectorized calculations.
  203.  
  204. *   Each function exists for every data type for which this is reasonable.
  205.     The data type is signalled by the prefix of the function name. No
  206.     implicit name mangling or other specific C++ features are used, which
  207.     makes VectorLib usable in C as well as in specific C++ programs.
  208.     Moreover, the names and the syntax of nearly all functions are the same
  209.     in C/C++, Pascal and Fortran languages.
  210.  
  211. *   Besides the vectorized complex functions, CMATH is included. This is a
  212.     library of complex operations and functions designed to be a faster,
  213.     safer and more complete replacement to the complex class libraries
  214.     shipped with C++ compilers. Moreover, CMATH does not require C++, but
  215.     may be used with simple C.
  216.  
  217. *   A large set of matrix operations is provided by MatrixLib, included
  218.     in the OptiVec package.
  219.  
  220.  
  221. As noted above, all functions, except some of the graphics and I/O routines,
  222. are written in Assembly language. This made optimizations possible which are
  223. not available in code produced by a compiler. You need not know any of the
  224. technical details described in the following lines and you may skip them,
  225. but perhaps these explanations will give you an idea of which performance
  226. to expect from VectorLib.
  227.  
  228. * Preload of floating-point constants
  229.   Floating-point constants, employed in the evaluation of mathematical
  230.   functions, are loaded onto the floating-point number stack outside of
  231.   the actual loop and stay as long as they are needed.
  232.   This saves a large amount of loading/unloading operations which are
  233.   necessary if a mathematical function is called for each element of a
  234.   vector separately.
  235.  
  236. * Full FPU stack usage
  237.   Where necessary, all eight coprocessor registers are employed. (For 
  238.   present compilers, it is already an excellent achievement to master 
  239.   the bookkeeping for only four coprocessor registers.)
  240.  
  241. * Superscalar scheduling
  242.   By careful  "pairing" of commands whose results do not depend upon each
  243.   other, the two integer pipes and the two fadd/fmul units of the
  244.   Pentium/Pentium Pro are used as efficiently as possible.
  245.   In most instances, computers equipped with 386/387 or 486DX CPUs just
  246.   will not care about these optimizations which they cannot profit from.
  247.   In those cases, however, where the performance on these older CPUs suffers
  248.   significantly from the Pentium-optimized scheduling, it is applied only in
  249.   the "4" version of OptiVec (back-compatible to 486DX), but not in the "3"
  250.   version (back-compatible to 386/387).
  251.  
  252. * Loop-unrolling
  253.   Where optimum pairing of commands cannot be achieved for single elements, 
  254.   vectors are often processed in chunks of two, four, or even more elements.
  255.   This allows to fully exploit the parallel-processing capabilities of the
  256.   Pentium and its successors.  Moreover, the relative amount of time spent
  257.   for loop management is significantly reduced.
  258.  
  259. * Simplified addressing
  260.   The addressing of vector elements is still a major source of inefficiency
  261.   with present compilers. Switching forth and back between input and output
  262.   vectors, a large number of redundant addressing operations is performed.
  263.   The strict (and easy!) definitions of all OptiVec functions allow to
  264.   reduce these operations to a minimum.
  265.  
  266. * Replacement of floating-point by integer commands
  267.   For any operations with floating-point numbers that can also be performed
  268.   using integer commands (like copying, swapping, or comparing to preset
  269.   values), the faster method is consistently employed.
  270.  
  271. * Strict precision control
  272.   C compilers convert a float into a double (Pascal: even into an extended),
  273.   before passing it to a mathematical function. This approach was useful at
  274.   times when disk memory was too great a problem to include separate
  275.   functions for each data type in the .LIB files, but it is simply
  276.   inefficient on modern PCs. Consequently, no such implicit conversions are
  277.   present in OptiVec routines. Here, a function of a float is calculated to
  278.   float (i.e. single) precision, wasting no time for the calculation of more
  279.   digits than necessary - which would be discarded anyway.
  280.  
  281. * All-inline coding
  282.   All external function calls are eliminated from the inner loops of the
  283.   vector processing. This saves the execution time necessary for the
  284.   call / ret  pairs and for passing the parameters forth and back.
  285.  
  286. * Cache-line matching of local variables
  287.   The Level-1 cache of the Pentium and its presently available successors
  288.   is organized in "lines" of 32 bytes each. Present compilers align the
  289.   stack on 4-byte boundaries, which means there is a 1-in-4 chance that
  290.   the 8 bytes of a double or the 10 bytes of an extended, stored on the
  291.   stack, will cross a 32-byte boundary. This, in turn, would lead to a
  292.   cache line-break penalty, deteriorating the performance. To avoid it,
  293.   OptiVec functions use special procedures to properly align their local
  294.   variables on 8 or 16-byte boundaries.
  295.  
  296. * Unprotected and reduced-range functions
  297.   For some mathematical functions, you have the choice between the fully
  298.   protected variant with error handling and another, extra-fast variant
  299.   without. Similarly, there are reduced-range versions of the sine and
  300.   cosine functions for those cases in which the user can guarantee all
  301.   input vector elements to lie in the range  -2 Pi <= x <= +2 Pi.
  302.   In these cases, the execution time may be reduced by up to 40% compared
  303.   to the full-range or fully protected version.
  304.  
  305. * Multithread support
  306.   With very few exceptions (namely the plotting functions, which have to
  307.   use global variables to store the current window and coordinate system
  308.   settings), all other OptiVec functions may run in parallel in different
  309.   threads. On multi-CPU configurations, this means the performance will
  310.   scale with the number of CPUs. OptiVec functions do not initiate threads
  311.   themselves, though, as the overhead involved in multi-threading would
  312.   significantly affect the performance on single-CPU machines. If you
  313.   have a multi-CPU computer, you have to explicitly launch the threads
  314.   you wish to run in parallel. For example, one thread might take the
  315.   lower half of the vector(s) you wish to process, while a second thread
  316.   takes the upper half - until a point is reached, where both must be
  317.   combined.
  318.  
  319. This documentation describes the OptiVec implementations for
  320.  
  321. - Borland C++ (Version 3.0 or higher, incl. Borland C++ Builder)
  322.   for DOS and Microsoft Windows 3.0 or later (or Win-OS sessions under
  323.   IBM OS/2 2.0 or later; in the following, we will simply speak
  324.   of "Windows"). The library for the memory model FLAT for Windows95/98 and
  325.   WindowsNT requires Borland C++, version 4.0 or higher.
  326.  
  327. - Microsoft Visual C++ (Version 5.0 or higher)
  328.   for Windows95/98/NT on PC platforms.
  329.  
  330. - Powersoft Optima++ (Version 1.5 or higher)
  331.   for Windows95/98/NT on PC platforms.
  332.  
  333. Please note that only the documentation is valid for these different
  334. compilers. The libraries themselves are compiler-specific; each library
  335. can be used only with one compiler and, in the case of Borland C++,
  336. with one memory model.
  337.  
  338. Borland C++ only:
  339. -----------------
  340.    Depending on your choice when ordering or downloading the Shareware
  341.    version,
  342.    you have got either of the following three library versions:
  343.    memory model FLAT for Windows95/NT, statically linked runtime library
  344.                 LARGE for DOS, or
  345.                 LARGE for Windows 3.x.
  346.    All of them require, at least, a 386 computer equipped with a 387
  347.    coprocessor. This means: no emulation, no 486SX, but preferably 486DX,
  348.    Pentium or higher.
  349.  
  350.    The full (registered) version contains libraries for all memory models of
  351.    DOS, 16-bit Windows and 32-bit Windows. These libraries, in turn, are
  352.    shipped in three versions:
  353.    one for 486DX and Pentium computers, the second for 386 with 387,
  354.    the third for 286 with or without coprocessor, i.e. with emulation.
  355.  
  356. Microsoft Visual C++ only:
  357. --------------------------
  358.    The Shareware version has libraries for "single-thread debug" and
  359.    "multi-thread debug". The full (registered) version for Microsoft
  360.    Visual C++ contains additional libraries for "multi-thread DLL debug"
  361.    and the three corresponding release libraries.
  362.    There is no actual debug information enclosed in the OptiVec "debug"
  363.    libraries, but they have to be used with the debug libraries of
  364.    Visual C++.
  365.  
  366.  
  367. Versions for other C compilers and for Pascal, Delphi, and Fortran are in
  368. preparation.
  369. For two-dimensional arrays, MatrixLib is included with OptiVec,
  370. offering optimized matrix operations like matrix arithmetics, algebra,
  371. decompositions, data fitting, etc. See MATRIX.TXT.
  372. TensorLib is planned as a future extension of these concepts for general
  373. multidimensional arrays.
  374.  
  375.  
  376. 1.2 Licence Terms
  377. -----------------
  378.  
  379. This is the English Shareware version of OptiVec ("SOFTWARE").
  380. It may be used under the following licence terms:
  381.  
  382. 1. You may test the SOFTWARE free of charge for an unlimited period of time.
  383.    This testing phase ends when you permanently integrate functions of this
  384.    SOFTWARE into any of your applications (programs, program parts...).
  385. 2. If you want to use this SOFTWARE for commercial purposes, you have
  386.    to purchase the commercial version (see chapter 1.3).
  387. 3. Use of this SOFTWARE for educational purposes at schools and universities
  388.    remains free of charge. However, if any application created under these
  389.    terms is sold to others or otherwise used for commercial purposes,
  390.    paragraph 2 applies.
  391. 4. Distributing this SOFTWARE to others is allowed only in one of the
  392.    following two ways:
  393.    a) linked into your programs, so that the parts stemming from this
  394.       SOFTWARE do no longer appear as a library.
  395.    b) as a whole in unchanged form (in particular the Copyright and Licence
  396.       statements!), whereby you may ask a fee only and exclusively for the
  397.       physical act of copying the SOFTWARE.
  398. 5. This SOFTWARE is provided on an "as is" basis. Any explicit or implicit
  399.    warranties for the SOFTWARE are excluded.
  400.    Despite thorough testing of the SOFTWARE, errors and bugs cannot
  401.    be excluded with certainty. No claims as to merchantability or fitness
  402.    for a particular purpose are made.
  403.    You may not use the SOFTWARE in any environment or situation where
  404.    personal injury or excessive damage to anyone's property (including
  405.    your own) could arise from malfunctioning of the SOFTWARE.
  406.  
  407.  
  408. Copyright for the SOFTWARE and its documentation (C) 1996-1999 Martin Sander
  409.  
  410. All rights reserved, including those of translation into foreign languages.
  411.  
  412. Address of the author:
  413.               Dr. Martin Sander Software Development
  414.               Sertürnerstr. 11
  415.               D-37085 Göttingen
  416.               Germany
  417.               e-mail: MartinSander@Bigfoot.com
  418.  
  419.  
  420.  
  421. 1.3 Registered Versions
  422. -----------------------
  423.  
  424. In order to make this product affordable also for those who will not
  425. themselves make money using it, we offer an "educational edition" at a
  426. strongly reduced rate, in addition to the full "commercial edition".
  427. The contents of these two editions is identical. The only difference lies
  428. in the restrictions of use: The "educational edition" may not be used for
  429. commercial / business / government purposes, but is restricted to private
  430. and educational use.
  431.  
  432. Purchasing the full (registered) version gives you the right to use it on
  433. as many computers at a time as the number of units you bought.
  434. Corporate site and world-wide licences are available upon request.
  435.  
  436. The full version (both the commercial and the educational editions)
  437. of OptiVec for Borland C++ and of OptiVec for Microsoft Visual C++
  438.  
  439. -  support all memory models of Windows95/98, NT, 3.x, and DOS
  440.    (Borland C++)
  441.    or single-thread, multi-thread, multi-thread DLL debug and release
  442.    (Microsoft Visual C++)
  443.  
  444. -  (Borland C++ only: )
  445.    have individually optimized libraries for each degree of processor
  446.    backward-compatibility:
  447.       486DX/Pentium+ (optimized for Pentium/PentiumPro)
  448.       386+ (387 coprocessor required)
  449.       286+ (no coprocessor required).
  450.  
  451. -  come with printed documentation.
  452.  
  453. -  entitle you to two free updates.
  454.  
  455. -  can be ordered at the following conditions:
  456.  
  457.    a) if you can pay in German Marks or Euro
  458.       and order directly from the author, the price is
  459.       DM  159,- /  EUR 81,50 for the educational edition,
  460.  
  461.       DM  299,- /  EUR 153,30 for  1 unit of the commercial edition
  462.       DM  999,- /  EUR 512,30 for  5 units,
  463.       DM 1799,- /  EUR 922,60 for 10 units
  464.          (incl. 16% VAT, plus DM 10,- / EUR 5,- handling charge).
  465.       Please order by sending an e-mail to MartinSander@Bigfoot.com
  466.       or use a print-out of the file ORDER.TXT.
  467.       Payment options:
  468.           - pre-paid by DM Eurocheque
  469.           - C.O.D. (Cash-On-Delivery)
  470.           - upon invoice (only within Germany, net 14 days)
  471.  
  472.       If you have a European VAT ID, or if you order from outside the
  473.       European Union, you are exempt from the German VAT, but you may
  474.       have to pay your local VAT and/or import duties according to
  475.       local laws.
  476.  
  477.    b) International credit card or USD cheque payment is possible by
  478.       ordering through ours or the following web-sites
  479.  
  480.       Atlantic Coast's SoftShop:
  481.       http://www.soft-shop.com/cgi-bin/order.html?136
  482.  
  483.       (this is the SoftShop sales page for all our products; please
  484.        be sure to choose the right one from the menu)
  485.  
  486.       $  89 for the educational edition,
  487.       $ 199 for  1 unit of the commercial edition,
  488.       $ 649 for  5 units,
  489.       $1199 for 10 units
  490.       Add $5 for S&H and applicable VAT.
  491.  
  492.       ShareIt:
  493.       OptiVec for Borland C++:
  494.          http://www.shareit.com/programs/101557.htm         (English handbook)
  495.          http://www.shareit.com/deutsch/programs/101556.htm (German handbook)
  496.       OptiVec for MSVC:
  497.          http://www.shareit.com/programs/103421.htm
  498.  
  499.       $  94 for the educational edition (including S&H),
  500.       $ 204 for the commercial edition (including S&H).
  501.             Add applicable VAT.
  502.  
  503.       You may also order by e-mail to register@shareit.com.
  504.       US customers can also call 1-800-903-4152 (only for orders, please).
  505.       US check and cash orders can be sent to ShareIt!'s US office at
  506.            ShareIt! Inc.
  507.            P.O. Box 97841 
  508.            Pittsburgh, PA 15227-0241
  509.            USA
  510.       * When ordering by e-mail, phone, or postal mail through ShareIt,  *
  511.       * please note the program number:                                  *
  512.       * OptiVec for Borland C++:    No. 101557                           *
  513.       *     dto., educational:      No. 102654                           *
  514.       * OptiVec for MSVC:           No. 103421                           *
  515.  
  516.  
  517. 1.4 Getting Started
  518. -------------------
  519.  
  520. To install OptiVec, please follow these steps:
  521.  
  522. 1.  In order to use OptiVec, you need an already installed copy of your
  523.     C/C++ compiler. Install OptiVec by executing INSTALL.EXE from the root
  524.     directory of the installation disk or CD-ROM. Normally, OptiVec will be
  525.     installed into a sub-directory named "OPTIVEC".
  526.  
  527. 2.  Add the OptiVec include and lib subdirectories to the library search
  528.     path and to the include-file search path, respectively.
  529.     For example, assuming you are using Borland C++ and the Borland C++
  530.     directory is C:\BC,  add
  531.        C:\BC\OPTIVEC\LIB       to the library search path  and
  532.        C:\BC\OPTIVEC\INCLUDE   to the include-file search path of the IDE
  533.                                (and of the configuration file TURBOC.CFG, in
  534.                                case you are using the command-line compiler).
  535.  
  536. 3.  Borland C++:
  537.       Choose the desired platform (DOS, Windows3.x, or Win32).
  538.       If you chose DOS or Windows3.x, select the memory model LARGE.
  539.       (For Win32, it is automatically FLAT; you should use static
  540.       linking and, if you use OptiVec's plotting functions, single-thread).
  541.       You should also choose, at least, 386 code generation and real
  542.       coprocessor commands (i.e., no emulation).
  543.     Microsoft Visual C++:
  544.       Choose "single-thread debug" or "multi-thread debug".
  545.  
  546. 4.  Add the desired OptiVec libraries to your project list.
  547.     Borland C++:
  548.        For DOS programs, these are
  549.            VCL3.LIB,  MCL3.LIB, and CMATHL3.LIB.
  550.        For Windows3.x, you need
  551.            VCL3W.LIB, MCL3W.LIB, and CMATHL3W.LIB.
  552.        Of course, if you do not use MatrixLib or CMATH, you do not need
  553.        to include their libraries.
  554.        For Win32 (Windows 95, 98, NT), please choose
  555.            VCF3W.LIB.
  556.            (For the 32-bit model, CMATH and MatrixLib are integrated
  557.             into the library VCF3W.LIB.)
  558.  
  559.     Microsoft Visual C++:
  560.        The library needed for single-thread debug is OVVCSD.LIB.
  561.        For multi-thread debug, you need OVVCMTD.LIB.
  562.  
  563. 5.  Use #include directives to declare VectorLib and CMATH functions by
  564.     including the header files described in chapter 7.
  565.     To get everything at once, declare
  566.         #include <VecAll.h>
  567.         #include <MatAll.h>.
  568.     If you are writing Borland C++ ObjectWindows applications, any OptiVec
  569.     header files should be included after the OWL header files.
  570.  
  571. 6. Borland C/C++ 16-bit programs only:
  572.     *   If the linker option "process extended dictionaries" is available
  573.         in your version of Borland C++, you must switch it on.
  574.         Otherwise, you might get a "Table limit exceeded" linker error.
  575.  
  576.     *   OptiVec works with Borland (Turbo) C++, version 3.0 or higher.
  577.         Since, from version 4.0 on, Borland changed the name of the error
  578.         handling routine matherr (without underbar) into _matherr (with a
  579.         leading underbar), any 16-bit program using CMATH has to call a macro,
  580.         NEWMATHERR, which takes  care of redirecting calls to _matherr,
  581.         if necessary. You should place the call to NEWMATHERR into the
  582.         module containing  main() or OwlMain():
  583.  
  584.              #include .....
  585.              #include <VecAll.h>
  586.              NEWMATHERR
  587.  
  588.              int main( void )
  589.              {    ..........   }
  590.  
  591.         If you forget to call NEWMATHERR, you will get a linker error
  592.         "Unresolved external _matherr" in the Borland C versions from 4.0 on.
  593.  
  594.         Inclusion of the macro NEWMATHERR is not needed for 32-bit programs.
  595.  
  596. After these preparations, all OptiVec functions are available for your
  597. programs.
  598.  
  599. Should you wish to remove OptiVec from your computer after testing, please
  600. simply delete the directory OPTIVEC with its subdirectories. The installation
  601. of OptiVec does not affect any files outside its own directory, so there
  602. is nothing else to get rid of.
  603.  
  604.  
  605.  
  606. ****************************************************************************
  607. *                                                                          *
  608. *******               2. Elements of VectorLib Routines              *******
  609. *                                                                          *
  610. ****************************************************************************
  611.  
  612. 2.1 The Data Types ui,  quad,  and extended
  613. -------------------------------------------
  614.  
  615. To increase the versatility and completeness of VectorLib, three additional
  616. data types are defined in <VecLib.h>:
  617.  
  618. The data type ui (short for "unsigned index") is used for the indexing of
  619. vectors and is defined as "unsigned int". However, in the HUGE model (sup-
  620. ported only in the registered version of VectorLib), ui is defined as
  621. "unsigned long", in order to correctly address huge arrays (greater than
  622. 64 kBytes, but with 16-bit addressing).
  623.  
  624. Starting already with the 8086/8087 processor pair, the Intel processors
  625. are able to process integer numbers of up to 64 bits (8 bytes). We call the
  626. 64-bit type "quad" (for "quadword integer"). It is not fully supported by
  627. Borland C++. Therefore, floating-point numbers (preferably long doubles
  628. with their 64-bit mantissa) have to be used as intermediates. The necessary
  629. interface functions, setquad, quadtod and _quadtold, are described in
  630. chapter 9.
  631. The type quad is always signed. There is not anything like an "unsigned quad".
  632.  
  633. The data type extended, which is familiar to Turbo Pascal users, is defined
  634. as a synonym for "long double" in OptiVec for Borland C++. As neither
  635. Visual C++ nor Optima++ support 80-bit reals, we define "extended" as
  636. "double" in the OptiVec versions for these compilers.
  637. The reason for the choice of the name "extended" is that all OptiVec
  638. routines shall have identical names in C/C++, Pascal and Fortran languages.
  639. Since the function prefixes are derived from the data types of the processed
  640. vectors (see below), this necessitates the definition of alias names for some
  641. data types denoted differently in the various languages. While the letter
  642. "L" (which could possibly stand for "long double") is already overcrowded by
  643. the data types long int and unsigned long, the letter "E" is unique to the
  644. data type extended and therefore used in the prefixes for vectors and
  645. functions of long double precision. This way, the letters defining the real-
  646. number data types are in alphabetical proximity: "D" for double, "E" for
  647. extended, and "F" for float. Maybe the future will bring high-precision
  648. 128-bit and 256-bit real numbers which could find their place in this series
  649. as "G" for "great" and "H" for "hyper".
  650.  
  651.  
  652.  
  653. 2.2 Complex Numbers:
  654. The Data Types fComplex,  dComplex,  eComplex
  655. ---------------------------------------------
  656.  
  657. Complex numbers are treated in C/C++ in quite a confusing way. ANSI C offers
  658. only a struct complex, Borland's C/C++ compiler additionally a struct
  659. _complexl for complex numbers of double and long double precision, resp.
  660. The real and imaginary parts are denoted as x and y.
  661. C++ offers a class complex which is of double precision; the real and
  662. imaginary parts are accessible via the functions real and imag. There is
  663. also a number of mathematical functions available for this class.
  664. Finally, the new Standard C++ library, included in Borland C++ 5, offers the
  665. classes complex<float>, complex<double>, and complex<long double>, equipped
  666. with basic functionality and the same range of mathematical functions
  667. as offered by the class complex.
  668.  
  669. Most compilers implement these functions very inefficiently and inaccurately.
  670. (Just writing down the textbook formula for a complex function, like it is
  671. usually done, works fine only for a very limited range of arguments!)
  672.  
  673. Our aims are
  674. *   to make the use of complex numbers of all three data types
  675.     possible in C as well as in C++,
  676. *   to allow for the most efficient implementation of all complex operations,
  677.     using assembler code instead of C++ templates,
  678. *   and to introduce an easy, compact and consistent nomenclature.
  679.  
  680. To this end, the new complex math library CMATH was created and is included
  681. in OptiVec. CMATH is described in greater detail in the file CMATH.TXT.
  682. If you use any of the non-vectorized functions contained in CMATH,
  683. you should include <newcplx.h> (for C++ modules) or <cmath.h> (for plain-C
  684. modules) before (!) any of the VectorLib include files.
  685.  
  686. VectorLib itself contains the necessary initialization functions of complex
  687. numbers and all vectorized forms of complex math functions. If you are using
  688. only these, you need not explicitly include CMATH. In this case, the
  689. following complex data types are defined in <VecLib.h>:
  690. typedef  struct { float     Re,  Im; }  fComplex;
  691. typedef  struct { double    Re,  Im; }  dComplex;
  692. typedef  struct { extended  Re,  Im; }  eComplex;
  693.  
  694. (the data type extended is used as a synonym for long double, see above.)
  695.  
  696. If, for example, a complex number z is declared as  "fComplex  z;", the real
  697. and imaginary parts of z are available as z.Re and z.Im, resp. Complex numbers
  698. are initialized either by setting the real and imaginary parts separately to
  699. the desired value, e.g.,
  700.     z.Re = 3.0;   z.Im = 5.7;
  701.  
  702. or, alternatively, the same initialization can be accomplished by the
  703. function fcplx:
  704.     z = fcplx( 3.0, 5.7 );
  705.  
  706. For double-precision complex numbers, use dcplx, for extended-precision
  707. complex numbers, use ecplx.
  708.  
  709. Pointers to arrays or vectors of complex numbers are declared using the data
  710. types cfVector, cdVector, and ceVector  described below.
  711.  
  712.  
  713.  
  714. 2.3 Vectors and Arrays:
  715. The Data Types  fVector,  dVector,  eVector,  cfVector,  cdVector,  ceVector,
  716.                 siVector, iVector,  liVector,  qiVector,
  717.                 usVector, uVector,  ulVector,  and  uiVector
  718. -----------------------------------------------------------------------------
  719.  
  720. We define, as usual, a "vector" as a one-dimensional array of data containing,
  721. at least, one element, with all elements being of the same data type. Using a
  722. more mathematical definition, a vector is a rank-one tensor. A two-dimensional
  723. array (i.e. a rank-two tensor) is denoted as a "matrix", and higher
  724. dimensions are always referred to as "tensors".
  725.  
  726. In contrast to other approaches, VectorLib does not allow zero-size vectors!
  727.  
  728. The basis of all VectorLib routines is formed by the various vector data
  729. types given below and declared in <VecLib.h>. In your programs, you may mix
  730. these vector types with the static arrays of classic C style.
  731. For example:
  732. float   a[100];           /* classic static array */
  733. fVector b=VF_vector(100); /* VectorLib vector */
  734. VF_equ1( a, 100 );      /* set the first 100 elements of a equal to 1.0   */
  735. VF_equC( b, 100, 3.7 ); /* set the first 100 elements of b equal to 3.7  */
  736.  
  737. In contrast to the fixed-size static arrays, the VectorLib types use dynamic
  738. memory allocation and allow for varying sizes. Because of this increased
  739. flexibility, we recommend that you predominantly use the latter.
  740. Here they are:
  741. typedef     float *            fVector;
  742. typedef     double *           dVector;
  743. typedef     long double *      eVector;
  744. typedef     fComplex *         cfVector;
  745. typedef     dComplex *         cdVector;
  746. typedef     eComplex *         ceVector;
  747. typedef     short *            siVector;
  748. typedef     int  *             iVector;
  749. typedef     long *             liVector;
  750. typedef     quad *             qiVector;
  751. typedef     unsigned short *   usVector;
  752. typedef     unsigned *         uVector;
  753. typedef     unsigned long *    ulVector;
  754. typedef     ui *               uiVector;
  755.  
  756. Thus, internally, a data type like fVector means "pointer to float", but
  757. you may think of a variable declared as fVector rather in terms of a
  758. "vector of floats". The data types ui, quad, fComplex, dComplex and eComplex
  759. themselves are described above.
  760.  
  761. Note: in connection with Windows programs, often the letter "l" or "L" is
  762. used to denote "long int" variables. In order to prevent confusion, however,
  763. the data type "long int" is signalled by "li" or "LI", and the data type
  764. "unsigned long" is signalled by "ul" or "UL".  Conflicts with prefixes for
  765. "long double" vectors are avoided by deriving these from the alias name
  766. "extended" and using "e", "ce", "E", and "CE", as described above and in the
  767. following.
  768.  
  769.  
  770.  
  771. 2.4 Real-number Functions:
  772.     The Prefixes VF_,  VD_,  and VE_
  773. ------------------------------------
  774.  
  775. The VectorLib package supports the three floating-point data types that are
  776. used by the coprocessors of the 80x87 family and the FPU units integrated
  777. into the 486DX and Pentium processors and their successors:  float,  double,
  778. and extended (i.e., long double).  BCD numbers are not supported.
  779.  
  780. Any of the algebraic and mathematical functions included in this library
  781. exists in one variant for each floating-point format. The data type of all
  782. floating-point vector elements, parameters, and of the return value is always
  783. the same within one function. The data type is signalled by the second letter
  784. of the prefix: VF_ denotes the variant of a function that uses exclusively
  785. the data type float, VD_ stands for the data type double, and VE_ for the
  786. data type extended, i.e., long double. (The first letter, "V", stands for
  787. "Vector function", of course.)  VF_ functions thus work on arrays declared as
  788. fVector, use parameters of the type float, and, if there is any floating-point
  789. return value, this will also be of the type float. There are no mixed-type
  790. functions (that would, e.g., work on vectors of type fVector, use parameters
  791. of type double and return a value of type long double).
  792.  
  793. One partial exception from this rule comes from the fact that floating-point
  794. return values of OptiVec functions are returned as long doubles on the number
  795. stack. Therefore, you may assign the return value of a function to a
  796. variable of another data type. For example, the product of all elements of a
  797. vector may easily overflow, and it is a good idea to define   eProd  as an
  798. extended (i.e., as a long double), before writing the line
  799.    eProd = VF_prod( X, size );  .
  800.  
  801. Borland C++ only: To use this possibility, you must switch the option
  802. "Fast floating point" on (in the IDE in the menu "Options/Compiler/Advanced
  803. Code Generation",  or the command-line compiler option "-ff"),
  804.  
  805. For the description of the functions in the Alphabetical Reference
  806. (chapter 8), generally only the VF_ version is described and its syntax
  807. explicitly given. The versions for the data types double and long double
  808. are exactly analogous to the VF_ variant. You have only to replace the
  809. prefix  "VF_" by  "VD_" (or  "VE_") and to use  "dVector" and "double"
  810. (or "eVector" and "extended", resp.) wherever you find "fVector" and "float"
  811. in the VF_ version.
  812.  
  813.  
  814.  
  815. 2.5 Complex-number Functions:
  816.     The Prefixes VCF_, VCD_, and VCE_
  817. --------------------------------------
  818.  
  819. Any prefix with its second letter being "C" denotes a function of complex
  820. numbers. By analogy with the nomenclature used for real-number functions, the
  821. prefix VCF_ signals the exclusive use of single-precision vectors, parameters
  822. and return values (fComplex, cfVector and float). Similarly, VCD_ is used for
  823. double-precision calculations, and VCE_ for extended precision. Wherever
  824. "fComplex", "cfVector", and "float" appear in the description of a function in
  825. the VCF_ version, the VCD_ and VCE_ versions are obtained by substituting with
  826. "dComplex",  "cdVector" and "double"  or "eComplex", "ceVector", and "extended"
  827. (or "long double"), resp.
  828.  
  829. Note: Return values of the data types fComplex, dComplex, and eComplex are
  830. not possible in Pascal/Delphi. Therefore, the syntax of those functions
  831. returning a complex number is different in C/C++ and Pascal/Delphi.
  832.  
  833. In contrast to the carelessness with which complex mathematical functions are
  834. often treated (see above), the complex functions of VectorLib are written
  835. such as to achieve full accuracy over the complete range of input/output
  836. values possible with the respective data type.
  837.  
  838. In order to perform non-vectorized complex operations with the same level
  839. of speed and reliability as the vectorized ones, use CMATH as a replacment
  840. of the complex class libraries. See the file CMATH.TXT for details.
  841.  
  842.  
  843.  
  844. 2.6 Functions of the Integer Data Types:
  845.     The Prefixes VI_, VBI_, VSI_, VLI_, VQI_, VU_, VUB_, VUS_, VUL_, and VUI_
  846. -----------------------------------------------------------------------------
  847.  
  848. The nomenclature for the integer data types is designed in a similar way as
  849. for the floating-point data types: VI_ indicates the use of the data type
  850. int, VBI_ stands for byte-sized int, VSI_ for short int, VLI_ for long int
  851. and VQI_ for quad integers. VU_ denotes operations with unsigned integers,
  852. VUB_ with unsigned byte, VUS_ with unsigned short and VUL_ is the prefix for
  853. functions of unsigned long arguments. For operations on index-arrays,
  854. functions with the prefix VUI_ allow to perform calculations using arguments
  855. of the data type ui defined above. The VUI_ versions are always defined as
  856. macros, and the compiler automatically substitutes either the VU_ or the VUL_
  857. version, whichever is appropriate for the memory model actually used.
  858.  
  859. Don't be afraid of so many data types. It is one of the advantages of C
  860. language to have them, and it is one of the disadvantages, at the same time,
  861. that a programming style is supported which mixes all the data types until
  862. it is no longer clear "who is who".  In all normal cases, the VI_, VLI_,
  863. VU_, and VUI_ functions should be sufficient; but keep in mind that there
  864. are more available in case you need them.
  865.  
  866. If present, the vectorized integer functions are always described together
  867. with their floating-point analogues. To obtain, for example, the VI_
  868. version, vectors of type iVector have to be substituted for those of type
  869. fVector which are demanded by the VF_ version. In the same way, the other
  870. versions are obtained by changing "float" and "fVector" into the desired
  871. data type.
  872.  
  873. Like the function names themselves, also the include-files in which the
  874. functions are declared are named according to the data type they belong to.
  875. Thus, the declarations for the functions of the data type int are to be
  876. found in <VIstd.h> and <VImath.h>, those of the data type unsigned long in
  877. <VULstd.h> and <VULmath.h>, and so on.
  878.  
  879.  
  880.  
  881. 2.7 Common Functions of Several Data Types:  The Prefix V_
  882. ----------------------------------------------------------
  883.  
  884. Several functions exist that are either used independently of any data type
  885. or that are used to interconvert the data types. Functions like V_initPlot
  886. and V_free belong to the first case (you have to initialize the plotting
  887. routines regardless of the data type of the vectors you are going to plot,
  888. and the initialization is not specific for any data type).
  889. A function like V_ULtoD  belongs to the second case; here, a  ulVector
  890. (a vector whose elements are of the data type unsigned long) is transformed
  891. into a dVector (a vector whose elements are doubles).
  892. The type-independent functions are declared in <VecLib.h> and <Vgraph.h>.
  893. The data-type interconversion functions are declared in the include-files
  894. belonging to the destination type (i.e. the type into which the numbers are
  895. converted).
  896.  
  897.  
  898. ****************************************************************************
  899. *                                                                          *
  900. *******                      3. The Environment                      *******
  901. *                                                                          *
  902. ****************************************************************************
  903.  
  904. 3.1 Borland C++ only:
  905.     The Different Library Versions:
  906.     Selecting Language, Memory Model, and Processor
  907. ---------------------------------------------------
  908.  
  909. The VectorLib routines may be used both in C and in C++ programs.
  910. Depending on your choice when ordering or downloading the Shareware version,
  911. you got one of the following three series of libraries:
  912.     VCF3W.LIB                            for Win32 (model FLAT of Windows95
  913.                                          and NT),
  914.     VCL3W.LIB + MCL3W.LIB + CMATHL3W.LIB for Windows3.x, model LARGE,
  915.     VCL3.LIB  + MCL3.LIB  + CMATHL3.LIB  for DOS Standard or DOS Overlay,
  916.                                          model LARGE.
  917.  
  918. The nomenclature of these libraries stems from the registered version which
  919. supports all memory models of DOS and Windows, each with its own set of
  920. libraries (for the three hardware configurations 486DX+, 386/387+, and 286+).
  921. The library name "VCL3W" means: [V]ectorLib for [C]/C++, memory model [L]arge,
  922. [3]86/387 processor or higher, for [W]indows programs. The names of the
  923. MatrixLib libraries begin with "MC..", the CMATH libraries with "CMATH..".
  924.  
  925. As has already been noted above, this Shareware version cannot be used on
  926. 286 machines and not on computers without coprocessor. In these cases, you
  927. would have to get, for example, the library VCL2.LIB of the registered
  928. version.
  929.  
  930.  
  931.  
  932. ****************************************************************************
  933. *                                                                          *
  934. *******           4. VectorLib Functions and Routines:               *******
  935. *******              A Short Overview                                *******
  936. *                                                                          *
  937. ****************************************************************************
  938.  
  939.  
  940. 4.1 Generation, Initialization and De-Allocation of Vectors
  941. -----------------------------------------------------------
  942.  
  943. With VectorLib, you may use static arrays (like, for example, float a[100];)
  944. as well as dynamically allocated ones (see chapter 2.3). We recommend,
  945. however, that you use the more flexible vector types defined by VectorLib,
  946. using dynamic allocation. This is described in the following sections.
  947. After a vector has been declared (e.g., as  fVector X; ), memory has to be
  948. allocated. When the vector is no longer needed, the memory it occupies has
  949. to be de-allocated again. For the allocation of memory, one specific function
  950. exists for each data type:  VF_vector,   VD_vector,  VI_vector,  and so on.
  951. If, together with the allocation, all elements shall be initialized with 0,
  952. VF_vector0,  VD_vector0,  VI_vector0,   etc. may be called.  To de-allocate
  953. memory, one and the same function is used for all data types:  V_free. In
  954. order to de-allocate several vectors with only one call, use V_nfree.
  955. V_freeAll frees all vectors at once.
  956.  
  957. Internally, the allocated vectors are written into a table to keep track
  958. of the allocated memory. If you try to free a vector that has never been
  959. or is no longer allocated, you get a warning message, and nothing is freed.
  960.  
  961. You might wonder why we add still more memory allocation functions to the
  962. already rich omnium gatherum of C and C++. The reason is that, for every
  963. environment and every memory model, the most appropriate memory management
  964. functions shall be selected automatically. This means that you, the user,
  965. need not deal yourself with the various methods, but can leave this task
  966. to VectorLib. Moreover, this makes your programs more easily portable.
  967. (Of course, the operator "new" offers similar benefits, but it is available
  968. only in C++. Since VectorLib shall be useable both in C and C++, it has
  969. to include its own functions for this purpose.)
  970.  
  971. The following functions are used to initialize or re-initialize vectors that
  972. have already been created:
  973. VF_equ0   sets all elements of a vector equal to 0;
  974. VF_equ1   sets them equal to 1;
  975. VF_equC   sets them equal to a constant.
  976. VF_equV   makes one vector a copy of another,
  977. VFx_equV  (the "expanded" version of the equality operation) relates each
  978.           element of a vector to the corresponding element of another
  979.           according to the formula  Yi = a * Xi + b.
  980.  
  981. VF_ramp   fills a vector with a "ramp" according to the formula  Xi = a*i + b.
  982. VF_random fills a vector with high-quality random numbers,
  983. VF_noise  with white noise, and
  984. VF_comb   with a "comb" function which, at equidistant points, equals a
  985.           constant C and is zero elsewhere.
  986.  
  987. VF_Hanning,  VF_Parzen, and VF_Welch are special functions creating so-called
  988. windows for use in spectral analysis (see VF_spectrum).
  989.  
  990. Complex vectors may be initialized by assigning the real and imaginary parts
  991. separately:  VF_ReImtoC,  VF_RetoC, and VF_ImtoC. Alternatively, they may be
  992. formed out of polar coordinates: VF_PolartoC.
  993.  
  994.  
  995.  
  996. 4.2 Index-oriented Manipulations
  997. --------------------------------
  998.  
  999. VF_rev       is used to reverse the ordering of the elements of a vector.
  1000. VF_reflect   sets the upper half of a vector equal to the reversed lower half.
  1001. VF_rotate    is used to rotate the ordering of the elements.
  1002. VF_insert    and
  1003. VF_delete    insert or delete an element of a vector.
  1004.  
  1005. VF_sort      is used for fast sorting of the elements into ascending or
  1006.              descending order. If only an index-array, but not the elements
  1007.              themselves are to be rearranged,
  1008. VF_sortind   does the job.
  1009. VF_subvector extracts a subvector from a (normally larger) vector, using a
  1010.              constant sampling interval.
  1011. VF_indpick   fills a vector with elements "picked" from another vector
  1012.              according to their indices.
  1013. VF_indput    is the complement of VF_indpick and distributes the elements of
  1014.              one vector to the sites of another vector specified by their
  1015.              indices.
  1016.  
  1017. Operations performed only on a sampled sub-set of elements of a vector are
  1018. provided by the   VF_subvector_...  family, where the omission mark stands
  1019. for a suffix denoting the desired operation.
  1020.  
  1021. VF_searchC   searches for the element of a vector that is closest to a
  1022.              pre-set value (with a parameter "mode" deciding if the closest,
  1023.              the closest larger-or-equal, or the closest smaller-or-equal
  1024.              value is chosen).
  1025. VF_searchV   does the same for a whole array of pre-set values.
  1026.  
  1027. Polynomial, rational, and cubic-spline interpolations are performed by
  1028. VF_polyinterpol,  VF_ratinterpol, and VF_splineinterpol, resp.
  1029.  
  1030.  
  1031.  
  1032. 4.3 Data-Type Interconversions
  1033. ------------------------------
  1034.  
  1035. The first thing that has to be said about the floating-point data-type
  1036. interconversions is: do not use them too extensively. Decide which accuracy
  1037. is appropriate for your application, and then use consistently either the
  1038. VF_, or the VD_, or the VE_ version of the functions you need. Nevertheless,
  1039. every data type can be converted into every other, in case it is necessary.
  1040.  
  1041. The functions used for the interconversion of the real-value floating-point
  1042. data types are: V_FtoD,  V_DtoF,  V_FtoE,  V_EtoF,  V_DtoE,  and V_EtoD.
  1043. Similarly, the following functions are offered for the complex floating-
  1044. point data types: V_CFtoCD,  V_CDtoCF,  V_CFtoCE,  V_CEtoCF,  V_CDtoCE,  and
  1045. V_CEtoCD.
  1046.  
  1047. Corresponding to the large number of integer data types, there is an even
  1048. larger number of functions interconverting them. Switching between "normal",
  1049. short, long and "quadruple" integers is performed by V_ItoLI,  V_ItoQI,
  1050. V_ItoSI,  V_SItoI,  V_SItoLI,  V_SItoQI,  V_LItoSI,  V_LItoI,  V_LItoQI,
  1051. V_QItoSI,  V_QItoI,  and V_QItoLI.
  1052.  
  1053. Similarly, the available types of unsigned numbers are interconverted by
  1054. V_UtoUL,  V_UtoUS,  V_UtoUI,  V_UStoU,  V_UStoUL,  V_UStoUI,  V_ULtoUS,
  1055. V_ULtoU,  V_ULtoUI, V_UItoU,  V_UItoUS,  and V_UItoUL.
  1056.  
  1057. Interconversions between signed and unsigned types can only be performed on
  1058. the same level of accuracy, namely by the functions V_ItoU,  V_UtoI,  V_LItoUL,
  1059. V_ULtoLI,  V_SItoUS,  and V_UStoSI.  That means that functions like V_UStoLI
  1060. do  n o t  exist!
  1061.  
  1062. The conversion of integers into floating-point types is accomplished by
  1063. V_ItoF,  V_ItoD,  V_ItoE,  V_SItoF,  V_SItoD,  V_SItoE,  V_LItoF,  V_LItoD,
  1064. V_LItoE,  V_QItoF,  V_QItoD,  V_QItoE,  V_UtoF,  V_UtoD,  V_UtoE,  V_UStoF,
  1065. V_UStoD,  V_UStoE,  V_ULtoF,  V_ULtoD,  V_ULtoE,  V_UItoF,  V_UItoD,   and
  1066. V_UItoE. Again, do not be confused by the large number of these functions,
  1067. but keep only in mind that for every interconversion there is one available.
  1068.  
  1069. The reverse process, the conversion of floating-point numbers into integers,
  1070. is more complicated: although every integer (except for extremely large
  1071. ones) has an exact representation in the floating-point types, this is not
  1072. true the other way round: floating-point numbers may by definition contain
  1073. fractional, i.e. "non-integer" parts. By choosing the appropriate rounding
  1074. function, the user has to decide how to treat these fractional parts:
  1075. Neglect them ("chop" or "trunc"), round to the nearest whole number ("round"),
  1076. round to the next greater-or-equal integer ("ceil") or to the next smaller-or-
  1077. equal integer ("floor"). These options are treated as mathematical functions
  1078. and are described in chapter 4.6.1.
  1079.  
  1080.  
  1081.  
  1082. 4.4 More about Integer Arithmetics
  1083. ----------------------------------
  1084.  
  1085. Although the rules of integer arithmetics are quite straightforward, it
  1086. appears appropriate to recall that all integer operations are implicitly
  1087. performed modulo 2**n, where n is the number of bits the numbers are
  1088. represented with. This means that any result, falling outside the range of
  1089. the respective data type, is made to fall inside the range by loosing the
  1090. highest bits. The effect is the same as if as many times 2**n had been added
  1091. to (or subtracted from) the "correct" result as necessary to reach the legal
  1092. range.
  1093. For example, in the data type short, the result of the multiplication 5 *
  1094. 20000 is  -31072. The reason for this seemingly wrong negative result is
  1095. that the "correct" result, 100000, falls outside the range of short numbers
  1096. which is -32768 <= x <= +32767.  short integers are 16-bit numbers, so n = 16,
  1097. and 2**n = 65536. In order to make the result fall into the specified range,
  1098. the processor "subtracts" 2 * 65536 = 131072 from 100000, yielding -31072.
  1099.  
  1100. Note that overflowing intermediate results cannot be "cured" by any following
  1101. operation. For example, (5 * 20000) / 4 is not (as one might hope) 25000,
  1102. but rather -7768.
  1103.  
  1104. Note furthermore that the 64-bit data type quad does not employ this implicit
  1105. modulo 2**n-arithmetics. Overflow conditions lead to undefined results.
  1106.  
  1107.  
  1108.  
  1109. 4.5 Basic Functions of Complex Vectors
  1110. --------------------------------------
  1111.  
  1112. The following functions are available for the basic treatment of complex
  1113. vectors.
  1114. VF_ReImtoC      forming a complex vector out of its real and imaginary parts,
  1115. VF_RetoC        overwriting the real part,
  1116. VF_ImtoC        overwriting the imaginary part,
  1117. VF_CtoReIm      extracting the real and imaginary parts,
  1118. VF_CtoRe        extracting the real part,
  1119. VF_CtoIm        extracting the imaginary part,
  1120. VF_PolartoC     forming a complex vector out of polar coordinates,
  1121. VF_CtoPolar     transforming a complex vector into polar coordinates,
  1122. VF_CtoAbs       calculating the absolute value (the magnitude of the pointer
  1123.                 in the complex plane),
  1124. VF_CtoArg       calculating the argument (the angle of the pointer in the
  1125.                 complex plane),  and
  1126. VF_CtoNorm      calculating the norm (which is defined here as the square of
  1127.                 the absolute value).
  1128.  
  1129.  
  1130.  
  1131. 4.6 Mathematical Functions
  1132. --------------------------
  1133.  
  1134. Lacking a more well-founded definition, we denote as "mathematical" all
  1135. those functions which calculate each single element of a vector from the
  1136. corresponding element of another vector by a more or less simple
  1137. mathematical formula:  Yi = f( Xi ).   Except for the "basic arithmetics"
  1138. functions, they are defined only for the floating-point data types. Most of
  1139. these mathematical functions are vectorized versions of ANSI C functions or
  1140. derived from them. Errors are handled by _matherr and _matherrl.  In
  1141. addition to this error handling "by element", the return values of the
  1142. VectorLib math functions show if all elements have been processed
  1143. successfully. If so, the return value is 0, otherwise it is any non-zero
  1144. int number.  (We do not yet use the newly introduced data type bool for
  1145. this return value, in order to make VectorLib compatible also with older
  1146. versions of C.)
  1147.  
  1148.  
  1149. 4.6.1 Rounding
  1150. --------------
  1151.  
  1152. As noted in connection with data-type interconversions, the conversion of
  1153. floating-point numbers to integer data types may be accomplished by four
  1154. different ways: Fractional parts may be neglected (VF_chop, VF_trunc), or
  1155. the numbers may be rounded to the nearest integer (VF_round),  to the next
  1156. greater-or-equal integer (VF_ceil), or to the next smaller-or-equal integer
  1157. (VF_floor).
  1158.  
  1159. The result of the rounding operation thus specified may either be left in
  1160. the original floating-point format, e.g., in VF_round, or it may be converted
  1161. into one of the integer types, as in VF_roundtoI,  VD_ceiltoLI, VF_choptoSI,
  1162. or VE_floortoQI. As long as the input numbers are positive, they can also be
  1163. rounded to the unsigned integer types,  as in VF_floortoU, VF_ceiltoUS,
  1164. VD_choptoUL, or VE_trunctoUI.
  1165.  
  1166.  
  1167.  
  1168. 4.6.2 Comparisons
  1169. -----------------
  1170.  
  1171. Functions performing comparisons are generally named VF_cmp... (where
  1172. further letters and/or numbers specify the type of comparison desired).
  1173. Every element of a vector can be compared either to 0, or to a constant C,
  1174. or to the corresponding element of another vector. There are two
  1175. possibilities: either the comparison is performed with the three possible
  1176. answers "greater than", "equal to" or "less than". In this case, the results
  1177. are stored as floating-point numbers (0.0,  1.0,  or -1.0). Examples are
  1178. VF_cmp0,  VD_cmpC,  and VE_cmpV.
  1179.  
  1180. The other possibility is to test if one of the following conditions is
  1181. fulfilled: "greater than", "greater than or equal to", "equal to", "not
  1182. equal to", "less than", or "less than or equal to". Here, the answers will
  1183. be "TRUE" or "FALSE" (1.0 or 0.0). Examples are VF_cmp_eq0,  VD_cmp_gtC, and
  1184. VE_cmp_leV.
  1185.  
  1186. Alternatively, the indices of the elements for which the answer was "TRUE"
  1187. may be stored in an index-array, as in VF_cmp_neCind, VD_cmp_lt0ind,  and
  1188. VE_cmp_geVind.
  1189.  
  1190. While the basic comparison functions check against one boundary, there is
  1191. a number of functions checking if a vector elements falls into a certain
  1192. range.
  1193. VF_cmp_inclrange0C   TRUE for 0 <= x <= C  (C positive),
  1194.                               0 >= x >= C  (C negative).
  1195. VF_cmp_exclrange0C   TRUE for 0 <  x <  C  (C positive),
  1196.                               0 >  x >  C  (C negative).
  1197. VF_cmp_inclrangeCC   TRUE for CLo <= x <= CHi,
  1198. VF_cmp_exclrangeCC   TRUE for CLo <  x <  CHi.
  1199.  
  1200. The variants of these functions that store the indices of elements yielding
  1201. "TRUE" are VF_cmp_inclrange0Cind, VF_cmp_exclrange0Cind,
  1202. VF_cmp_inclrangeCCind, and VF_cmp_exclrangeCCind.
  1203.  
  1204. To test if (at least) one element of a table is equal to a preset value, the
  1205. function VF_iselementC may be used. In order to test for each element of a
  1206. vector, if it has an identical entry in a table, VF_iselementV should be
  1207. used.
  1208.  
  1209.  
  1210.  
  1211. 4.6.3 Direct Bit-Manipulation
  1212. -----------------------------
  1213.  
  1214. For the integer data types, a number of bit-wise operations is available:
  1215. VI_shl and VI_shr shift the bits to the left or to the right, resp., which
  1216. is used for the fast multiplication and division by integer powers of 2.
  1217. The principal use of VI_and is the fast modulo division of positive or
  1218. unsigned numbers, while VI_or,  VI_xor, and VI_not  will find use only in
  1219. special applications.
  1220.  
  1221.  
  1222.  
  1223. 4.6.4 Basic Arithmetics, Accumulations
  1224. --------------------------------------
  1225.  
  1226. In the following list, only the VF_ function is explicitly named, but the
  1227. VD_ and VE_ functions exist as well; if it makes sense, the same is true for
  1228. the complex and for the integer-type versions:
  1229.  
  1230. VF_neg        Yi = - Xi;
  1231. VF_abs        Yi = │ Xi │;
  1232. VCF_conj      Yi.Re = Xi.Re; Yi.Im = -(Xi.Re).
  1233. VF_inv        Yi = 1.0 / Xi;
  1234. VF_equC       Xi = c;                VF_equV     Yi = Xi;
  1235. VF_addC       Yi = Xi + c;           VF_addV     Zi = Xi + Yi;
  1236. VF_subC       Yi = Xi - c;           VF_subV     Zi = Xi - Yi;
  1237. VF_subrC      Yi = c - Xi;           VF_subrV    Zi = Yi - Xi;
  1238. VF_mulC       Yi = Xi * c;           VF_mulV     Zi = Xi * Yi;
  1239. VF_divC       Yi = Xi / c;           VF_divV     Zi = Xi / Yi;
  1240. VF_divrC      Yi = c / Xi;           VF_divrV    Zi = Yi / Xi;
  1241. VF_modC       Yi = Xi mod c;         VF_modV     Zi = Xi mod Yi.
  1242.  
  1243. Besides these basic operations, several frequently-used combinations of
  1244. addition and division have been included, not to forget the Pythagoras
  1245. formula:
  1246.  
  1247. VF_hypC    Yi = Xi / (Xi + c);        VF_hypV    Zi =  Xi / (Xi + Yi);
  1248. VF_redC    Yi = (Xi * c) / (Xi + c);  VF_redV    Zi =  (Xi * Yi) / (Xi + Yi);
  1249. VF_visC    Yi = (Xi - c) / (Xi + c);  VF_visV    Zi =  (Xi - Yi) / (Xi + Yi);
  1250. VF_hypotC  Yi = sqrt( Xi² + c² );     VF_hypotV     Zi =   sqrt( Xi² + Yi²).
  1251.  
  1252. All functions in the right column of the above two sections also exist in an
  1253. expanded form (with the prefix VFx_...) in which the function is not
  1254. evaluated for Xi itself, but for the expression (a * Xi + b),  e.g.,
  1255. VFx_addV:   Zi  =  (a * Xi + b) + Yi.
  1256.  
  1257. The simple algebraic functions exist also in yet another special form,
  1258. with the result being scaled by some arbitraty factor. This scaled
  1259. form gets the prefix VFs_.
  1260. VFs_addV     Zi = C * (Xi + Yi);
  1261. VFs_subV     Zi = C * (Xi - Yi);
  1262. VFs_mulV     Zi = C * (Xi * Yi);
  1263. VFs_divV     Zi = C * (Xi / Yi);
  1264.  
  1265. VF_maxC     sets Yi equal to Xi or C, whichever is greater;
  1266. VF_minC     chooses the smaller of Xi and C;
  1267. VF_maxV     (and  VF_minV) set Zi equal to Xi or Yi, whichever is greater
  1268.             (or smaller, resp.).
  1269. VF_limit    limits the range of values, while
  1270. VF_flush0   sets all values to zero which are below a preset threshold.
  1271. VF_intfrac  splits the numbers into their integer and fractional parts;
  1272. VF_mantexp  splits the numbers into their mantissa and exponent parts.
  1273.  
  1274. In its geometrical interpretation, a vector is a pointer, with its elements
  1275. representing the coordinates of a point in n-dimensional space. There are a
  1276. few functions for geometrical vector arithmetics, namely
  1277. VF_scalprod,  which calculates the scalar product of two vectors,
  1278. VF_xprod,     which calculates the cross-product (or vector product) of two
  1279.               vectors, and
  1280. VF_Euclid,    calculating the Euclidean norm of a vector.
  1281.  
  1282. While, in general, all OptiVec functions are for input and output vectors
  1283. of the same type, there exists one family of functions for the accumulation
  1284. of data in either the same type or in higher-precision data types.
  1285. These functions correspond to the operation Y += X.
  1286. The same-type variant is called VF_accV;  examples for the mixed-type
  1287. forms are VD_accVF, VF_accVI, and VQI_accVLI.
  1288.  
  1289.  
  1290. 4.6.5 Powers
  1291. ------------
  1292.  
  1293. VF_square,  VF_cubic, and VF_quartic, along with their expanded versions
  1294. VFx_square,  VFx_cubic,  and VFx_quartic, are used to calculate the second,
  1295. third and fourth power of the elements of the input vector. Arbitrary
  1296. integer powers are available by VF_ipow; fractional powers are calculated by
  1297. VF_pow. Polynomials are evaluated by VF_poly.
  1298.  
  1299. In situations where you can be absolutely sure that all input elements
  1300. yield valid results, you may employ the "unprotected" versions of the
  1301. integer power functions: VFu_square, VFu_cubic, VFu_quartic, VFu_ipow,
  1302. VFu_poly, with their expanded counterparts denoted by the prefix VFux_ .
  1303. Due to the much more efficient vectorization permitted by the absence of
  1304. error checks, the unprotected functions are up to 1.8 times as fast as the
  1305. protected versions. (This is true from the Pentium CPU on; on older computers,
  1306. almost nothing is gained.) Be, however, aware of the price you have to
  1307. pay for this increase in speed: in case of an overflow error, the program
  1308. will crash without any warning.
  1309.  
  1310. All these functions raise arbitrary numbers to specified powers, whereas the
  1311. following group of functions is used to raise specified numbers to arbitrary
  1312. powers: VF_pow10, VF_ipow10,  VF_pow2,  and VF_ipow2  raise 10 or 2, resp.,
  1313. to the (fractional or integer) powers specified in the input vector.
  1314. The exponential function, VF_exp, raises Euler's constant e to the powers
  1315. specified in the input vector. Finally, VF_expArbBase calculates the
  1316. exponential function of an arbitrary base.
  1317.  
  1318. The square-root, which corresponds to a power of 0.5,  is available with
  1319. VF_sqrt.
  1320.  
  1321. The corresponding functions for complex numbers are VCF_square,  VCF_cubic,
  1322. VCF_quartic,  VCF_ipow,  VCF_pow,  VCF_exp,  VCF_expArbBase, and VCF_sqrt.
  1323.  
  1324.  
  1325.  
  1326. 4.6.6 Exponentials and Hyperbolic Functions
  1327. -------------------------------------------
  1328.  
  1329. A variety of functions are derived from the exponential function VF_exp (which
  1330. itself has already been mentioned in the last section).
  1331. VF_expc   calculates the complementary exponential function Yi = 1 - exp[Xi].
  1332. VF_expmx2 calculates the exponential function of the negative square of the
  1333.           argument,  Yi = exp[ - Xi² ]. This is a bell-shaped function similar
  1334.           to the Gaussian distribution function which itself is available as
  1335. VF_Gauss.
  1336.  
  1337. Related to VF_Gauss and to VF_exp, the error function and the complementary
  1338. error function are calculated by VF_erf and VF_erfc, respectively.
  1339.  
  1340. The vectorized hyperbolic sine, cosine, tangent, cotangent, secant, and
  1341. cosecant functions are available as VF_sinh, VF_cosh, VF_tanh, VF_coth,
  1342. VF_sech, and VF_cosech. Because of its importance in physics, the squared
  1343. hyperbolic secant is also available as VF_sech2.
  1344.  
  1345. For complex numbers,  VCF_sinh,  VCF_cosh,  and VCF_tanh are available.
  1346.  
  1347.  
  1348.  
  1349. 4.6.7 Logarithms
  1350. ----------------
  1351.  
  1352.            The decadic logarithm (i.e., the logarithm to the basis 10) is
  1353.            available as
  1354. VF_log10,  the natural logarithm (i.e., to the basis e) is obtained by
  1355. VF_log,    and the binary logarithm (i.e., to the basis 2) is implemented as
  1356. VF_log2.   Similarly, for complex numbers,
  1357. VCF_log,  VCF_log10, and VCF_log2  (as always with their VCD_ and VCE_
  1358.            counterparts) are included.
  1359.  
  1360. As a special form of the decadic logarithm, the Optical Density,
  1361. OD = log10( X0/X ), is calculated by  VF_OD  (for floating-point input
  1362. vectors) and VUS_ODtoF, VUB_ODtoF etc. (for unsigned-integer input vectors).
  1363. VF_ODwDark, VUS_ODtoDwDark, etc. allow to calculate the OD with a correction
  1364. for dark currents.
  1365.  
  1366.  
  1367. 4.6.8 Trigonometric Functions
  1368. -----------------------------
  1369.  
  1370. The vectorized sine, cosine, tangent, cotangent, secant, and cosecant
  1371. functions are available as
  1372. VF_sin,       VF_cos,
  1373. VF_sincos     (sine and cosine at once!),
  1374. VF_tan,       VF_cot,
  1375. VF_sec,       and VF_cosec.
  1376.  
  1377. The squares of the trigonometric functions are available by
  1378. VF_sin2,      VF_cos2,
  1379. VF_sincos2    (again both the sin² and the cos² at once),
  1380. VF_tan2,      VF_cot2,
  1381. VF_sec2,      and VF_cosec2.
  1382.  
  1383. In cases where one knows beforehand that all input elements are witin a
  1384. range -Pi/2 <= x <= +Pi/2,  one can spare quite considerable execution
  1385. time in the calculation of the sine and cosine functions by employing
  1386. the "reduced-range" functions
  1387. VFr_sin,   VFr_cos,   VFr_sincos,
  1388. VFr_sin2,  VFr_cos2,  VFr_sincos2,
  1389. along with their expanded counterparts, denoted by the prefix VFrx_ .
  1390. Please note that especially the implementation chosen for the 32-bit
  1391. model FLAT will crash without warning in the case of any input number
  1392. outside the range specified above.
  1393. As all other trigonometric functions need error checking and handling,
  1394. even for arguments within this range, no reduced-range versions of the
  1395. trigonometric functions, aside from the sine and the cosine, have been
  1396. included.
  1397.  
  1398. A very efficient way to calculate the trigonometric functions for arguments
  1399. representable as rational multiples of Pi is supplied by the trigonometric
  1400. functions with the suffix "rpi" (meaning "rational multiple of pi"):
  1401. VF_sinrpi, VF_cosrpi, VF_sincosrpi, VF_tanrpi, VF_cotrpi, VF_secrpi, and
  1402. VF_cosecrpi.
  1403. More specialized versions use tables to obtain frequently-used values;
  1404. these versions are denoted by the suffixes "rpi2" (multiples of Pi divided
  1405. by an integer power of 2) and "rpi3" (multiples of Pi over an integer
  1406. multiple of 3). Examples are VF_sinrpi2 and VF_tanrpi3.
  1407.  
  1408. The sinc function (quotient of the sine of an argument and the argument
  1409. itself) is available as the VF_sinc.
  1410.  
  1411. The Kepler function (angular position of a planet with time, given its
  1412. round-trip time and eccentricity, according to Kepler's Second Law) is
  1413. implemented as VF_Kepler.
  1414.  
  1415. Vectorized inverse trigonometric functions are available as VF_asin,
  1416. VF_acos, VF_atan, and VF_atan2.
  1417.  
  1418. Complex trigonometric and inverse trigonometric functions are implemented as
  1419. VCF_sin,  VCF_cos,  VCF_tan,  VCF_asin,  VCF_acos,  and VCF_atan.
  1420.  
  1421.  
  1422.  
  1423. 4.7 Analysis
  1424. ------------
  1425.  
  1426. Global maxima and minima of real functions are detected by VF_max and
  1427. VF_min, resp. The same extrema, along with the index of their first
  1428. occurrence, are detected by VF_maxind and VF_minind, resp. To find the
  1429. maxima and minima in terms of absolute values, the functions VF_absmax and
  1430. VF_absmin are included along with the versions additionally yielding the
  1431. index, VF_absmaxind and VF_absminind. The "running" maximum and minimum
  1432. (where each element is set to the largest/smallest value occurring up to its
  1433. own index) are calculated by VF_runmax and VF_runmin, resp.
  1434.  
  1435. For complex numbers, the maximum real and imaginary parts may be found
  1436. separately by VCF_maxReIm, with the analogous function for the minima being
  1437. VCF_minReIm. For the separately-found maxima and minima of the real and
  1438. imaginary parts in absolute terms, use VCF_absmaxReIm and VCF_absminReIm.
  1439. Note that, for these four functions, the real and imaginary parts of
  1440. the result generally stem from different elements of the vector.
  1441.  
  1442. The largest absolute value (magnitude) occurring in a set of complex data is
  1443. found by VCF_absmax, the smallest one by VCF_absmin. To find the index of
  1444. the element with the largest/smallest magnitude along with that magnitude,
  1445. use VCF_absmaxind and VCF_absminind, resp.
  1446.  
  1447. The sum of all elements of a real or complex vector is available by VF_sum
  1448. and its higher-accuracy or complex analogues, the product by VF_prod and the
  1449. sum-of-squares by VF_ssq.  A summation over absolute values is performed
  1450. by VF_sumabs. VF_rms determines the r.m.s. of all elements of a vector.
  1451. Similarly to the "running" maximum, the running sum and product are available
  1452. by VF_runsum and VF_runprod, resp.
  1453.  
  1454. The derivative of a Y-array with respect to an X-array is calculated by
  1455. VF_derivV. If the intervals between the X-values are constant, the values
  1456. themselves are not needed for taking the derivative, but only the spacing is
  1457. required; VF_derivC should be employed in this case.
  1458. The integral of a Y-array over an X-array is calculated by the two functions
  1459. VF_integralV and VF_runintegralV, of which the first one determines only the
  1460. area under the curve defined by the input array, whereas the second one
  1461. calculates the point-by-point integral array. As for the derivative, also for
  1462. the integral the X-values themselves are not needed if they are equally-
  1463. spaced; in this case, VF_integralC and VF_runintegralC should be used.
  1464.  
  1465. VF_ismomoton   tests if an array is monotonously rising or falling.
  1466. VF_smooth      (which removes high-frequency noise),
  1467. VF_iselementC  (which tests, if a given value occurs within a vector), and
  1468. VF_searchC     (which searches an ordered table for the entry whose value
  1469.                comes closest to a preset value C) have to be mentioned as
  1470.                functions sometimes needed in connection with analysis.
  1471.  
  1472.  
  1473.  
  1474. 4.8 Signal Processing:
  1475.     Fourier Transforms and Related Topics
  1476. -----------------------------------------
  1477.  
  1478. The forward and the backward Fast Fourier Transform (FFT) are calculated by
  1479. VF_FFT or, for complex vectors, by VCF_FFT.
  1480.  
  1481. Based on FFT, convolution and deconvolution are available by
  1482. VF_convolve and VF_deconvolve.
  1483. Spectral filtering is achieved by VF_filter,
  1484. spectral analysis by VF_spectrum.
  1485. The autocorrelation function of a data array is obtained by VF_autocorr,
  1486. and the cross-correlation function of two arrays by VF_xcorr.
  1487.  
  1488. The FFT algorithm chosen for this PC implementation is a radix-2
  1489. Cooley-Tukey routine. Only for this radix-2 algorithm, the restricted
  1490. number of eight coprocessor registers still allows to hold all inter-
  1491. mediate results of the inner transform loop in coprocessor registers.
  1492. Although featuring savings in the number of multiplications, radix-4 and
  1493. radix-8 routines are rendered less efficient than the routine chosen by
  1494. the need of storing intermediate results in memory.
  1495.  
  1496. There are two different versions of all FFT-based functions. Depending
  1497. on the memory model, either of the two is automatically chosen. You
  1498. may, however, explicitly specify the one you wish to employ.
  1499. The first one uses the already-mentioned table of sine values (see
  1500. chapter 4.6.8. and the function VF_sinrpi2) as a look-up table for the
  1501. Fourier coefficients needed. This table needs up to 10 kBytes.
  1502. By default, this very fast variant is used in the memory models COMPACT
  1503. and LARGE. To explicitly specify it in the other memory models, please use
  1504. the prefixes VFl_, VDl_, VEl_ (with the letter "l" for the "larger" amount
  1505. of memory needed). 
  1506.  
  1507. The second variant, which is automatically chosen in all memory models
  1508. except for COMPACT and LARGE, employs trigonometric recursions to obtain the
  1509. sine and cosine values with still satisfactory speed, though this procedure
  1510. is not as fast as simply reading them from a table. You may explicitly
  1511. specifiy this variant by adding the letter "s" (for the "smaller" amount of
  1512. memory needed) in the function prefix. Examples are VFs_FFT, VDs_convolve,
  1513. VEs_spectrum.
  1514. If you decide to use this variant in order to economize memory in the models
  1515. COMPACT and LARGE, use the prefix VFs_ for all(!) routines employing FFT.
  1516. Otherwise, you will not only load the look-up table, but also a second FFT
  1517. routine into your already overcrowded memory.
  1518.  
  1519. Although it does not use Fourier transform methods, VF_smooth should be
  1520. remembered here as a crude form of frequency filtering which removes high-
  1521. frequency noise.
  1522.  
  1523.  
  1524.  
  1525. 4.9 Statistical Functions and Building Blocks
  1526. ---------------------------------------------
  1527.  
  1528. The mean (or average) of all the elements of a vector is obtained by
  1529. VF_mean; if different weights are to be attributed to the individual
  1530. elements, VF_meanwW ("mean with weights") may be used. The variance of a
  1531. distribution with respect to a preset constant value is calculated by
  1532. VF_varianceC (with weights by VF_varianceCwW), the variance with respect to
  1533. another array by VF_varianceV and VF_varianceVwW. To obtain the mean and the
  1534. variance of a distribution simultaneously, VF_meanvar and VF_meanvarwW are
  1535. used.
  1536. VF_meanabs calculates the mean of the absolute values.
  1537. If outlier points are to be excluded from the calculation of the mean,
  1538. VF_selected_mean allows to average only those vector elements which fall
  1539. into a specified range.
  1540.  
  1541. The median of a distribution is found by VF_median.
  1542.  
  1543. The linear correlation coefficient of two distributions is available by
  1544. VF_corrcoeff.
  1545.  
  1546. VF_sumdevC   sums up the deviations from a preset constant, sum( │Xi - C│ ).
  1547. VF_sumdevV   sums up the deviations from another vector, sum( │Xi - Yi│ ).
  1548. VF_avdevC    gives the "average deviation from a preset constant",
  1549.                      1/N * sum( │Xi - C│ ), and
  1550. VF_avdevV    gives the "average deviation from another vector",
  1551.                      1 / N * sum( │Xi - Yi│ ).
  1552. VF_ssqdevC   yields the "sum of the squares of the deviations from a preset
  1553.              constant",  sum( (Xi - C)² ),
  1554. VF_ssqdevV   the "sum of the squares of the deviations from another vector",
  1555.              sum( (Xi - Yi)² ).
  1556. VF_chi2      calculates the chi-square merit function, while
  1557. VF_chiabs    calculates a more "robust" merit function, summing up absolute
  1558.              instead of squared deviations.
  1559.  
  1560.  
  1561. A linear regression is performed on X-Y data by VF_linregress or, if the
  1562. individual data points are to be weighted, by VF_linregresswW.
  1563.  
  1564. Fitting of data sets to arbitrary functions is available in MatrixLib,
  1565. which contains the functions VF_polyfit, VF_linfit, VF_nonlinfit,
  1566. VF_multiLinfit, and VF_multiNonlinfit (see MATRIX.TXT).
  1567.  
  1568. VF_distribution bins data into a discrete one-dimensional distribution
  1569. function.
  1570.  
  1571. In connection with statistics, the functions VF_sum, VF_prod, VF_ssq,
  1572. VF_rms, and VF_iselementC should be remembered.
  1573.  
  1574.  
  1575.  
  1576. 4.10 Input and Output
  1577. ---------------------
  1578.  
  1579. There are several ways of printing the elements of a vector:
  1580. VF_cprint   prints them to the screen (or "console" - hence the "c" in the
  1581.             name) into the current text window, automatically detecting its
  1582.             height and width. After printing one page, the user is prompted
  1583.             to continue.
  1584. VF_print    is similar to VF_cprint in that the output is directed to the
  1585.             screen, but there is no automatic detection of the screen data;
  1586.             a default linewidth of 80 characters is assumed, and no division
  1587.             into pages is made.
  1588.             Both VF_print and VF_cprint should not be used within TurboVision.
  1589.             VF_cprint is not available under Windows. VF_print is available
  1590.             for DOS and EasyWin applications, but not for genuine (i.e., OWL)
  1591.             Windows programs.
  1592. VF_fprint   prints a vector to a stream. This may be a file, a printer, or
  1593.             again the screen. Nothing will prevent you from mis-using this
  1594.             function for printing to the screen in TurboVision or Windows,
  1595.             but you should not!
  1596.             VF_fprint is available in any environment (DOS, EasyWin and OWL).
  1597.  
  1598. VF_write   writes data in ASCII format in a stream
  1599. VF_read    reads a vector from an ASCII file.
  1600. VF_nwrite  writes n vectors of the same data type as the columns of a table
  1601.            into a stream.
  1602. VF_nread   reads the columns of a table into n vectors of the same type.
  1603.  
  1604. VF_setWriteFormat, VF_setWriteSeparate and VF_setNWriteSeparate allow
  1605. to modify the standard settings of VF_write and VF_nwrite.
  1606. For the whole-number variants of the ..read functions, a radix different
  1607. from the standard of 10 may be defined using V_setRadix.
  1608. V_setRadix does, however, not act on VQI_read.
  1609.  
  1610. VF_store and VF_recall are employed to store and retrieve data in binary
  1611. format (which is much faster and occupies fewer bytes of disk space than
  1612. ASCII format).
  1613.  
  1614.  
  1615.  
  1616. 4.11 Graphics
  1617. -------------
  1618.  
  1619. VectorLib includes a range of data-plotting routines.
  1620. Before any of them may be used, VectorLib graphics has to be initialized.
  1621.  
  1622. For Windows programs, VectorLib graphics has to be initialized by V_initPlot.
  1623. No shut-down is needed at the end, since the Windows graphics functions
  1624. always remain accessible.
  1625.  
  1626. For DOS programs, this is done by V_initGraph. By calling V_initGraph, the
  1627. BGI functions (on which VectorLib's graphics functions rely) are
  1628. automatically initialized, too. Do not call initgraph after V_initGraph.
  1629. If you have already called initgraph, do not use V_initGraph, but V_initPlot
  1630. instead of it. At the end of the graphics session, the Borland C function
  1631. closegraph has to be used to leave the graphics mode and to release graphics
  1632. buffer memory.
  1633.  
  1634. Windows and DOS:
  1635. V_initPlot automatically reserves a part of the screen for plotting
  1636. operations. This part comprises about 2/3 of the screen on the right side.
  1637. Above, one line is left for a heading. Below, a few lines are left empty.
  1638. To change this default plotting region, call V_setPlotRegion after V_initPlot.
  1639.  
  1640. Only under Windows, all VectorLib plotting functions may directly be
  1641. used for printing on a printer. If this is desired, you have to call
  1642. V_initPrint instead of V_initPlot. By default, one whole page is reserved
  1643. for plotting. In order to change this, call V_setPlotRegion after V_initPrint.
  1644.  
  1645. VectorLib distinguishes between two sorts of plotting functions,
  1646. AutoPlot  and  DataPlot.
  1647.  
  1648. All AutoPlot functions (e.g., VF_xyAutoPlot) execute the following steps:
  1649. *   define a viewport within the plotting region (which is either the
  1650.     default region or the one defined by calling V_setPlotRegion)
  1651. *   clear the viewport
  1652. *   generate a Cartesian coordinate system with suitably scaled and labeled
  1653.     axes
  1654. *   plot the data according to the parameters passed to the function
  1655.  
  1656. All DataPlot functions (e.g. VE_yDataPlot) execute only the last of these
  1657. steps. They assume that a coordinate system already exists from a previous
  1658. call to one of the AutoPlot functions. The new plot is added to the existing
  1659. one. All settings of this coordinate system have to be valid. The viewport
  1660. must still be the active one and the scaling of the axes has to fit also for
  1661. the new data plot.
  1662.  
  1663. To add text and lables, a new viewport must be defined.
  1664. Use setviewport (DOS), SetViewportOrg (Windows with OWL 1.0), or
  1665. SetViewportOrgEx (Windows with OWL 2.0 or higher).
  1666.  
  1667. To switch back into text mode in DOS, use restorecrtmode.
  1668. After that, calling V_initPlot brings you back into graphics mode.
  1669.  
  1670. VF_xyAutoPlot   displays an automatically-scaled plot of an X-Y vector pair.
  1671. VF_yAutoPlot    plots a single Y-vector, using the index as X-axis.
  1672. VF_xy2AutoPlot  and
  1673. VF_y2AutoPlot   plot two X-Y pairs or two Y-vectors at once, doing the
  1674.                 necessary scaling so that both fit into the same coordinate
  1675.                 system.
  1676.                 To plot additional arrays into an already existing coordinate
  1677.                 system,
  1678. VF_xyDataPlot   and
  1679. VF_yDataPlot    should be used, as has already been mentioned.
  1680.  
  1681. Complex arrays are printed into the complex plane (the imaginary parts
  1682. versus the real parts), using
  1683. VCF_autoPlot,  VCF_2AutoPlot,  and  VCF_dataPlot.
  1684.  
  1685. The different plot styles, regarding symbols, lines, and colors, are
  1686. described in connection with VF_xyAutoPlot in the Function Reference
  1687. (file FUNCREF.TXT, chapter 8).
  1688.  
  1689. It is possible to draw more than one coordinate systems into a given
  1690. window on the screen. The position of each coordinate system must be
  1691. specified by the above-mentioned function V_setPlotRegion. "Hopping"
  1692. between the different coordinate systems and adding new DataPlots
  1693. after defining new viewports (e.g., for text output) is made possible
  1694. by the following functions:
  1695. V_continuePlot    go back to the viewport of the last plot and restore
  1696.                   its scalings
  1697. V_getCoordSystem  get a copy of the scalings and position of the current
  1698.                   coordinate system
  1699. V_setCoordSystem  restore the scalings and position of a coordinate system;
  1700.                   these must have been stored previously, using
  1701.                   V_getCoordSystem
  1702.  
  1703. DOS only:
  1704. When using multiple coordinate systems on the same screen, the default font
  1705. used for axis labeling might be too large, so that neighbouring labels
  1706. overlap each other. In these cases, use the BGI function settextstyle to
  1707. switch to another font befor calling a VectorLib AutoPlot function.
  1708.  
  1709.  
  1710. ****************************************************************************
  1711. *                                                                          *
  1712. *******                     5. Error Handling                        *******
  1713. *                                                                          *
  1714. *****************************************************************************
  1715.  
  1716. 5.1 General Remarks
  1717. -------------------
  1718.  
  1719. There are generally two types of error handling: by the hardware, or by the
  1720. software. In order to prevent uncontrolled program crash, it is highly
  1721. desirable that conditions, leading to hardware errors, be recognized before
  1722. the errors actually occur. All high-level computer languages support this
  1723. software error-handling to various degrees of perfection. Within the
  1724. tightly-defined functions and routines of this VectorLib package, often an
  1725. even more efficient error handling by the program itself is possible than
  1726. provided by the compilers for user-written code.
  1727.  
  1728. However, it should be noted that no absolute overflow protection is possible
  1729. for the long double versions. They do not have a "safety margin" left as in
  1730. the float and double versions, where internally all calculations are performed
  1731. in extended precision. Especially the VEx_ and VCEx_versions may fail if
  1732. constant parameters are very large, or if the X vector elements themselves are
  1733. already near the overflow limit. To be on the safe side, constant parameters
  1734. should not exceed about 1.E32 for float, 1.E150 for double, and 1.E2000 for
  1735. extended parameters.
  1736.  
  1737. In the "expanded" versions of all functions with extended accuracy (those
  1738. with the prefixes VEx_  and VCEx_;  for example VEx_exp), there is generally
  1739. no overflow protection for the calculation of A*Xi+B, but only for the core
  1740. of the function itself and for the final multiplication by C.
  1741.  
  1742. A series of identical errors occurring within one and the same VectorLib
  1743. function leads to one error message only. Subsequent identical messages are
  1744. suppressed.
  1745.  
  1746. There is a fundamental difference between floating-point and integer numbers
  1747. with respect to OVERFLOW and DOMAIN errors: for floating-point numbers,
  1748. these are always serious errors, whereas for integer numbers, by virtue of
  1749. the implicit modulo-2**n arithmetics, this is not necessarily the case. In the
  1750. following two paragraphs, details are given on the error handling of integer
  1751. and floating-point numbers, respectively.
  1752.  
  1753.  
  1754.  
  1755. 5.2 Integer Errors
  1756. ------------------
  1757.  
  1758. The only genuine integer errors are ZERODIVIDE errors (if a division by 0 is
  1759. attempted). Other integer errors are neglected due to the implicit definition
  1760. of integer operations to be done modulo the respective power of 2 (see
  1761. chapter 4.4). For those situations in which implicit modulo 2**n arithmetics
  1762. is not appropriate, VectorLib offers the possibility to trap these errors and
  1763. print an error message and/or abort the program. All functions where
  1764. INTEGER OVERFLOW (e.g., in VI_ramp, VI_mulV, etc.) or INTEGER DOMAIN errors
  1765. (e.g., in V_ItoU for negative X-values) may occur, exist in two versions:
  1766. the "normal" version employs modulo 2**n arithmetics and interchanges signed
  1767. and unsigned data types according to their bit pattern.
  1768.  
  1769. For the 16-bit and 32-bit integer types (but not for 8-bit and 64-bit),
  1770. there is a second version which also employs modulo 2**n arithmetics, but
  1771. detects the errors. To choose this version, the symbolic constant
  1772. V_trapIntError must be defined before(!) <VecLib.h> appears in the program
  1773. header.
  1774.  
  1775. The action taken in case of INTEGER OVERFLOW errors is then defined by a call
  1776. to the function  V_setIntErrorHandling  with one of three possibilities as
  1777. the argument (defined as enum V_ihand in <VecLib.h>):
  1778.  
  1779. ierrNote      print an error message
  1780. ierrAbort     print an error message and exit the program
  1781. ierrIgnore    ignore the problem. With this last option, the error handling
  1782.               can be switched off intermediately.
  1783.  
  1784. Example:
  1785.     #define V_trapIntError 1
  1786.     #include <VIstd.h>
  1787.     #include <VImath.h>
  1788.     .....
  1789.     main()    /*   or WinMain(),  or OwlMain()   */
  1790.     {
  1791.         iVector  I1, I2;
  1792.         I1 = VI_vector( 1000 );  I2 = VI_vector( 1000 );
  1793.         V_setIntErrorHandling( ierrNote );
  1794.         VI_ramp( I1, 1000, 0, 50 );   /* an overflow will occur here! */
  1795.         V_setIntErrorHandling( ierrIgnore );
  1796.         VI_mulC( I2, I1, 1000, 5 );
  1797.             /* here, even a whole series of overflows will occur; they are
  1798.                all ignored. */
  1799.          ....
  1800.     }
  1801.  
  1802.  
  1803.  
  1804. 5.3 Floating-Point Errors
  1805. -------------------------
  1806.  
  1807. In order to understand the details of the floating-point error handling
  1808. outlined in the following sections, you may wish to refer to the description
  1809. of the functions _matherr and signal in the documentation of your C++
  1810. compiler.
  1811. (Borland C++ only: prior to the version 4.0, instead of _matherr() the
  1812. function matherr() - without the leading underbar - was used, see below).
  1813. Keep in mind that _matherr and _matherrl are the user-definable focal points
  1814. for the handling of all software-detected errors, whereas signal is used to
  1815. install a handler for hardware-detected errors (which should better be
  1816. avoided in the first place). Within the VectorLib functions, _matherr is
  1817. used for the error handling in the VF_, VCF_, VD_, and VCD_ versions. 
  1818. _matherrl is used in the VE_ and VCE_ versions (Borland C++ only, as
  1819. neither Visual C++ nor Optima++ support 80-bit real numbers).
  1820.  
  1821. Below, the possible types of errors are described. Here, we denote by
  1822. "HUGE_VAL" the largest number possible in the respective data type,
  1823. i.e. MAX_FLT, MAX_DBL, or MAX_LDBL. Similarly, "TINY_VAL" is the smallest
  1824. denormal number representable in the respective data type. This is not the
  1825. same as MIN_VAL, which is the smallest full-accuracy number of the respective
  1826. data type.
  1827.  
  1828. If the function in which an error occurs has one real-valued argument, only
  1829. the parameter e->x is defined in calling _matherr and e->y  is left undefined.
  1830. Only if there are two arguments (like in VF_atan2  or in VF_cotrpi),
  1831. both e->x  and e->y are needed to hold these arguments. For complex arguments,
  1832. the real part is stored in e->x  and the imaginary part in e->y.
  1833.  
  1834. For each function of the VectorLib package, the types of errors that are
  1835. detected and handled are described in the "Alphabetical Reference" (chapter 8).
  1836. All functions derived from ANSI C functions of the mathematical libraries
  1837. (those whose declarations are to be found in <math.h>)  contain a fully-
  1838. fledged mathematical error handling. In addition to the error handling
  1839. "by element", their return value shows if all elements have been processed
  1840. error-free (return value 0) or if an error occurred and was handled (return
  1841. value different from 0).
  1842.  
  1843. DOMAIN errors most often lead to the result NAN ("not-a-number"). Even if
  1844.     nothing happens within the function itself that detects a DOMAIN error,
  1845.     an uncontrolled program crash may result if subsequent operations are
  1846.     performed on the vector element set to NAN. We therefore recommend to
  1847.     modify _matherr and _matherrl in such a way that the program is aborted
  1848.     if a DOMAIN error occurs (for an example, see below; alternatively, the
  1849.     UNIX style may be adopted; see the file MATHERR.C supplied with the
  1850.     your C/C++ compiler). Changing the return value of _matherr is another
  1851.     possiblity, but the better way very clearly is to avoid any DOMAIN errors
  1852.     by performing appropriate checks before calling functions like VF_sqrt,
  1853.     VF_log, VF_atan2 etc.
  1854.        Note:  the pseudo-numbers INF and NAN are not allowed as input for any
  1855.        functions of the VectorLib library. They are not tested for; their
  1856.        presence will normally result in a hardware interrupt.
  1857.  
  1858. SING errors are treated like an extreme case of OVERFLOW (see below). In
  1859.     most cases, they arise from an implicit division by zero or from taking
  1860.     the logarithm of zero. The proposed result is never NAN, but always a
  1861.     "number", in most cases ±HUGE_VAL. Although it is recommended also in the
  1862.     case of SING errors to abort the program and take the necessary measures
  1863.     to avoid them, you may choose to continue program execution.
  1864.  
  1865. OVERFLOW errors are the most abundant form of floating-point errors. They
  1866.     are always handled by proposing +HUGE_VAL or -HUGE_VAL as the result.
  1867.     Within many user algorithms, OVERFLOW  errors may occur for intermediate
  1868.     results; if subsequent steps perform operations like taking the inverse,
  1869.     the final result may be acceptable despite the error. Therefore, we
  1870.     recommend to accept the return-value proposal and not to abort the
  1871.     program.
  1872.  
  1873. In principle, you may decide not to accept the return-value proposal of
  1874. _matherr, but to substitute another one. However, for several reasons
  1875. you are discouraged from doing that: the correct sign of the result is
  1876. set by the calling ("complaining") function in many cases only after
  1877. returning from _matherr;  the x-value passed to _matherr (which should
  1878. be inspected before the return value is modified) may either be X[i]
  1879. or (as in some of the expanded complex math functions of the VCEx_...
  1880. family) the intermediate result x' = Ax + B.  Note, furthermore, that
  1881. all x-values are passed to _matherr as double-precision floating-point
  1882. numbers, also in the case of integer input numbers (like in VF_tanrpi,
  1883. where P[i] and q are passed as x and y to _matherr).
  1884.  
  1885. TLOSS  ("total loss of precision") errors are handled by  _matherr only if a
  1886.     more serious error might occur in the respective function. For example,
  1887.     the sine function takes on values between -1 and +1 for all arguments.
  1888.     So, in case of an argument too big for the sine function to be evaluated
  1889.     with any accuracy, the result may nevertheless be "tacitly" set to 0.0
  1890.     and no call to _matherr is generated (whereas Borland C++ chooses NAN,
  1891.     "not a number", as the result, which is certainly even less correct than
  1892.     arbitrarily choosing 0.0).
  1893.     On the other hand, the cosecant, i.e. the inverse of the sine, is not
  1894.     defined for arguments of integer multiples of Pi. Therefore, a more
  1895.     serious error (in this case a SING or an OVERFLOW error) might be hidden
  1896.     under the TLOSS for very big arguments. This possibility is taken into
  1897.     account by calling _matherr, although the proposed result is again set
  1898.     to 0.0 (which is the mean of the two extremes +HUGE_VAL and -HUGE_VAL).
  1899.     Generally, the default result in the case of a TLOSS error is the mean of
  1900.     the results for arguments of +0.0 and -0.0.
  1901.  
  1902. UNDERFLOW errors are never detected; underflowing results are always
  1903.     "tacitly" set to denormal numbers or finally to 0.0 by the floating-point
  1904.     processor itself. Indeed, you may very rarely wish to do something else
  1905.     in this case.
  1906.  
  1907. As in all non-vectorized math functions of Borland C++, PLOSS ("partial loss
  1908. of precision") errors are never detected and precision problems simply
  1909. ignored.
  1910.  
  1911.  
  1912. 5.3.1 Borland C++ only:
  1913.       Differences between Borland C++ 4.0 and earlier versions
  1914. --------------------------------------------------------------
  1915.  
  1916. Borland C++ uses the function _matherr in the way described above only
  1917. from version 4.0 on. Earlier versions employ the function matherr
  1918. (without the leading underbar in the function name). In order to be
  1919. usable both with the new and the old versions, VectorLib primarily
  1920. calls matherr as for the older versions. The include-file <VecLib.h>
  1921. provides a macro NEWMATHERR for the redirection of these calls to the
  1922. new _matherr(). This macro should appear somewhere in the module
  1923. containing the main() or WinMain() procedure, after the header:
  1924.     #include <VecLib.h>
  1925.     #include ...
  1926.     NEWMATHERR
  1927.       ......
  1928.     main()
  1929.     { ... }
  1930.  
  1931.  
  1932.  
  1933. 5.4 The Treatment of Denormal Numbers
  1934. -------------------------------------
  1935.  
  1936. "Denormal" are very small numbers between zero and the smallest full-
  1937. accuracy number available in the respective data type.  You may
  1938. understand the underlying principle from a simplified example:
  1939. 1.175494E-38 is the smallest "normal" float, with 7-digit accuracy.
  1940. What about 1/1024 of this value? This can only be represented as
  1941. 0.001145E-38, which is accurate to only four digits, since the first
  1942. three digits are needed to hold zeros. Thus, denormal numbers provide a
  1943. smooth transition between the smallest representable normal numbers and
  1944. zero.
  1945.  
  1946. In general, they may be treated just as ordinary numbers. In some instances,
  1947. however, like taking the inverse, overflow errors may occur. In these cases,
  1948. the somewhat academic distinction between SING and OVERFLOW errors is dropped
  1949. and a SING error signalled (as if it was a division by exactly 0).
  1950.  
  1951. On the other hand, for functions like the logarithms, very small input numbers
  1952. may give perfectly reasonable results, although the exact number 0.0 is an
  1953. illegal argument, leading to a SING error. Here, the possible loss of
  1954. precision is neglected and denormals are considered valid arguments.
  1955. (This treatment is quite different from that chosen for the math functions of
  1956. Borland C/C++, where denormal arguments lead to SING errors also in these
  1957. cases, which seems less appropriate to us.)
  1958.  
  1959.  
  1960.  
  1961. 5.5 Advanced Error Handling: Writing Messages into a File
  1962. ---------------------------------------------------------
  1963.  
  1964. ANSI C provides the user-definable function perror to print error messages.
  1965. However, most compilers do not use perror for this purpose. This means that
  1966. the way error messages are printed is not controllable by the programmer.
  1967. While this is fine in most instances, there may be situations in which you
  1968. might, for example, wish the error messages not to be printed to the screen,
  1969. but rather into a file, so that you could check later what has gone wrong.
  1970. An additional motivation could come from the fact that, for any error
  1971. occurring in a Windows program, a message box is displayed and program
  1972. execution interrupted until you acknowledge having taken notice of the error.
  1973.  
  1974. You might wish to circumvent this. To this end, VectorLib provides the
  1975. function  V_setErrorEventFile. This function needs as arguments the desired
  1976. name of your event file and a switch named ScreenAndFile which decides if the
  1977. error message is printed only into the file, or additionally to the screen
  1978. as well.
  1979.  
  1980. Note that this redirection of error messages is valid only for errors
  1981. occurring in VectorLib routines. If you wish to do so, however, there is a
  1982. way to extend the redirection also to the "non-VectorLib" functions:  you
  1983. may modify  _matherr and _matherrl such that the statement
  1984.     return 0;
  1985. (which signals an unresolved error)  is replaced by the sequence
  1986.     V_noteError( e->name, e->type ); return 1;
  1987. Thereby the task of printing the error message for unresolved errors is
  1988. passed to the VectorLib function V_noteError. Keep in mind that it is the
  1989. return value of _matherr which decides if an error message is printed by the
  1990. default error handler of your compiler. Thus, after the call to V_noteError,
  1991. the printing of the default error messages is by-passed by returning "1".
  1992. (Also, do not forget that VectorLib uses your _matherr routine to determine
  1993. which errors you accept and which not!)
  1994.  
  1995. For example, your _matherr function (matherr - without the leading underbar
  1996. - for Borland C++ 3.0 and 3.1) might look like the following one:
  1997.  
  1998.     #include <math.h>
  1999.     int  _matherr( struct exception *e)
  2000.     {
  2001.         if( (e->type == UNDERFLOW) ││ (e->type == TLOSS) ) ;    /* ignore */
  2002.         else   /* all other errors deserve at least notice */
  2003.         {
  2004.               V_noteError( e->name, e->type );
  2005.               if (e->type == DOMAIN) exit(1); /* really fatal */
  2006.         }
  2007.         return 1;
  2008.     }
  2009.  
  2010. (Of course, if you decide to change _matherr, do not forget to change
  2011. _matherrl in the same way!).
  2012.  
  2013. The default printing of error messages on the screen alone is restored by
  2014. V_closeErrorEventFile.
  2015.  
  2016. A way to keep track also of those errors which do not lead to messages is
  2017. opened by the return values of mathematical VectorLib functions. Any of the
  2018. "silent" TLOSS along with the more serious DOMAIN, SING and OVERFLOW errors
  2019. will lead to a non-zero return value. You may wish to check for a clean
  2020. result after a group of functions, like in the following example:
  2021.  
  2022.    unsigned ErrFlag;
  2023.    ...
  2024.          /*   part Trig1  */
  2025.    ErrFlag=0;   /* reset the flag */
  2026.    ErrFlag |= VF_sin( Y1, X1, sz );
  2027.    ErrFlag |= VF_cos( Y2, X1, sz );
  2028.    ErrFlag |= VF_atan2( Z1, Y1, Y2, sz );
  2029.    if( ErrFlag ) printf( "Errors occurred in part Trig1 ! ");
  2030.    ...
  2031.  
  2032. As indicated in the example, it is better to use the   |=  operator instead
  2033. of  +=  (since,  in rare cases, all return values might add up to 65536,
  2034. which is stored as 0 due to an overflow of the integer variable). Even if
  2035. you chose addition of the individual return values, the number of occurred
  2036. errors would not be obtainable from the result; in case of an error, any
  2037. non-specified non-zero number is returned.
  2038.  
  2039.  
  2040.  
  2041. ****************************************************************************
  2042. *                                                                          *
  2043. *******                    6. Trouble-Shooting                       *******
  2044. *                                                                          *
  2045. ****************************************************************************
  2046.  
  2047.  
  2048. 6.1 General Problems
  2049. --------------------
  2050.  
  2051. In case of problems, please check first if VectorLib is correctly installed
  2052. (see chapter 1.4). If this is the case, carefully check the following points
  2053. whose violation would inevitably lead to failure.
  2054.  
  2055. *   The choice of the VectorLib library must match your selection of memory
  2056.     model, processor, and environment. With Borland C++, you are not going
  2057.     to have much fun with the library VCL3.LIB under Windows3.x (where you
  2058.     need VCL3W.LIB), and the libraries designed for Borland C++ will not
  2059.     work with Visual C++ or any other compiler. Similarly, OVVCSD.LIB,
  2060.     designed for single-thread debug in Visual C++, will not work in any
  2061.     multi-thread or any "release" link.
  2062.  
  2063. *   You must not use vectors with a size of 0. All functions tacitly assume
  2064.     that the vectors have at least one element and do not waste your computer
  2065.     time testing for that.
  2066.  
  2067. *   You must not use vectors that are only declared, but have no allocated
  2068.     memory (see the description of VF_vector). If you did not switch off
  2069.     warnings, you may be warned also by the compiler not to do that
  2070.     ("possible use of xxx before definition").
  2071.  
  2072. *   Constant parameters should not exceed 1.E32 for floats, 1.E150 for
  2073.     doubles,  or 1.E2000 for long doubles. Normally, these ranges should
  2074.     suffice for any application...
  2075.  
  2076. *   16-bit Borland C++ only: Do not forget to write the line
  2077.         NEWMATHERR
  2078.     after the header into the module containing main(),  WinMain(),  or
  2079.     OwlMain(), in order to maintain compatibility both with older and later
  2080.     versions of Borland C++  (see chapter 5.3.1).
  2081.  
  2082. Although VectorLib has been tested very thoroughly, there is, of course,
  2083. always the possibility that a problem might have escaped our attention.
  2084. Should you feel you discovered a "bug" in VectorLib, please try to specify
  2085. the situation causing the problem as exactly as possible and let the author
  2086. know!
  2087.  
  2088.  
  2089.  
  2090. 6.2 Problems with Windows3.x?
  2091. -----------------------------
  2092.  
  2093. Programming for 16-bit Windows is much more involved than programming for
  2094. either DOS or 32-bit Windows. While DOS gives the programmer almost complete
  2095. control over both the main processor and the coprocessor, Windows demands
  2096. much of this control for itself. This introduces problems you should be
  2097. aware of. They are not at all specific to VectorLib. However, since they
  2098. seem not to be very widely known, here is a collection of some of them.
  2099. Up to now, these problems have not been observed with the memory model FLAT
  2100. used with Win32 (Microsoft's 32-bit extension of Windows 3.1), Windows NT
  2101. or Windows95/98.
  2102.  
  2103. *   The background routines controlling intermediate results do not only work
  2104.     at the expense of your time, they may also at some point decide to load a
  2105.     NULL selector into the segment registers FS and GS. If you happen to use
  2106.     these registers (somehow, they were meant by Intel to be used!), Windows'
  2107.     answer on your next operation will be the familiar "General Protection
  2108.     Fault (Error 13)". Therefore, the Windows versions of VectorLib do not
  2109.     use FS and GS at all.
  2110.  
  2111. *   If a floating-point multiplication or division happens to result in a
  2112.     so-called "denormal number" (see chapter 5.4), Windows at first accepts
  2113.     this result. The next time you use this denormal result, however, Windows
  2114.     decides that it had better been zero. Checking for zero by a comparison
  2115.     like
  2116.           if(x != 0.0)...
  2117.     yields the correct answer that x it is not zero, but, after (!) this
  2118.     check, Windows makes x exactly zero, if it is loaded onto the number
  2119.     stack. This leads to hard-to-find errors. If you inspect VectorLib
  2120.     routines with the debugger, you may at some points encounter strange,
  2121.     seemingly ineffecient code being used for comparisons. This is a fix for
  2122.     the described problem which costs time, but saves you from Windows-
  2123.     induced DIVIDE ERROR crashes.
  2124.  
  2125. *   Related to the last problem is another feature of Windows3.x: after the
  2126.     comparison of two floats or two doubles, one of which is denormal, -NAN
  2127.     ("minus not-a-number")  may appear on the number stack. Some time later,
  2128.     this leads to a "Floating-point invalid" or a "Stack Overflow" error -
  2129.     another means of killing your application. If you encounter -NAN on the
  2130.     number stack when debugging your programs (with or without VectorLib
  2131.     used), you should find out which comparison(s) caused the problem and add
  2132.     the line
  2133.            asm  ffree ST(0);
  2134.     after this or these comparisons.
  2135.  
  2136.  
  2137.  
  2138. 6.3 Problems with Borland's 16-bit Linker?
  2139. ------------------------------------------
  2140.  
  2141. When working with large programs and libraries, older versions of TLINK
  2142. sometimes run into problems. You may get error messages like "Linker stack
  2143. overflow", "Out of memory", "Table limit exceeded", "Extended dictionaries
  2144. ignored", or "Unresolved external xxx referenced from module yyy".
  2145.  
  2146. Try to give the linker as much memory as possible by closing applications,
  2147. removing drivers etc. If that does not help, re-arrange your project list.
  2148. Curiously enough, that solves the problem sometimes.
  2149.  
  2150. In the case of "Unresolved external" linker errors, there is only one way
  2151. (if the error is not caused by wrong spelling). First you have to use TLIB
  2152. in order to get a listing of the respective library (see the description of
  2153. TLIB !). Screening the .LST file thus obtained with a text editor, you find
  2154. the module containing the symbol which the linker was unable to locate.
  2155. Using again TLIB, you have to extract this module from the library and add
  2156. the resulting .OBJ file to your project list.
  2157.  
  2158.  
  2159. 7. The include-files of VectorLib
  2160. ---------------------------------
  2161.  
  2162. The prototypes for the VectorLib routines are to be found in the include-
  2163. files described below. If you are using MFC (Microsoft Foundation Classes)
  2164. or Borland's OWL (ObjectWindows Library), the MFC or OWL include-files have
  2165. to be included before (!) the VectorLib include-files.
  2166.  
  2167. <VecLib.h> contains the basic definitions of the data types along with the
  2168. prototypes of the functions common to all data types (prefix V_) except for
  2169. the graphics initialization functions. The trigonometric tables (see chapter
  2170. 4.6.8) and the few non-vectorized math functions needed internally by
  2171. VectorLib  (see chapter 9), are made publically accessible and are declared
  2172. in <xmath.h>.
  2173.  
  2174. <newcplx.h> is the complex class library CMATH replacing your compiler's
  2175. <complex.h> for C++ modules.
  2176. <cmath.h> and its "children" <cfmath.h>, <cdmath.h> and <cemath.h>
  2177. are the CMATH include files for plain-C modules.
  2178.  
  2179. <VIstd.h>, <VBIstd.h>,  <VSIstd.h>, <VLIstd.h>, <VQIstd.h>,
  2180. <VUstd.h>, <VUBstd.h>,  <VUSstd.h>, <VULstd.h>, <VUIstd.h>,
  2181. <VFstd.h>,  <VDstd.h>,  <VEstd.h>,
  2182. <VCFstd.h>, <VCDstd.h>,  and <VCEstd.h>
  2183. contain the prototypes of the functions used for the generation and
  2184. initialization of vectors, for index-oriented manipulations, data-type
  2185. interconversions, and I/O operations. For the floating-point data types,
  2186. they also contain the prototypes of routines for statistics, analysis,
  2187. geometrical vector arithmetics, and Fourier-Transform related functions. In
  2188. <VFstd.h>, the real-number functions for the data type float (prefix VF_)
  2189. are to be found, in <VDstd.h> those for the data type double, and so on.
  2190.  
  2191. The algebraic and mathematical functions are declared in the <V..math.h>
  2192. header files:
  2193. <VImath.h>,  <VBImath.h>,  <VSImath.h>,  <VLImath.h>,  <VQImath.h>,
  2194. <VUmath.h>,  <VUBmath.h>,  <VUSmath.h>,  <VULmath.h>,  <VUImath.h>,
  2195. <VFmath.h>,  <VDmath.h>,   <VEmath.h>,
  2196. <VCFmath.h>, <VCDmath.h>,  and  <VCEmath.h>.
  2197.  
  2198. <Vgraph.h> contains the prototypes of the graphics and plotting routines for
  2199. all data types.
  2200.  
  2201.  
  2202. *****************************************************************************
  2203.  
  2204.  
  2205. For detailed information on each single function of VectorLib, see the
  2206.  
  2207. S e c o n d  P a r t :  File  FUNCREF.TXT
  2208.  
  2209.  8.  Alphabetical Reference
  2210.  
  2211.  9.  Non-vectorized Functions
  2212.  
  2213. 10.  VectorLib Error Messages
  2214.  
  2215.  
  2216. *****************************************************************************
  2217.  
  2218. Copyright (C) Martin Sander 1996-1999
  2219.